
    #Zj                    0   d Z ddlZddlZddlZddlZddlZddlZddlZddlm	Z	m
Z
mZmZmZ ddlZddlZddlZddlZddlZddlZddlZddlZddlmZmZ ddlZddlmZmZmZ ddlmZ ddl Z ddl!m"Z" dd	l#m$Z$ dd
l%m&Z'm(Z(m)Z) ddl*m+Z+ ddl!m,Z, ddl-m.Z.m/Z/m0Z0m1Z1m2Z2  e3            Z4g dZ5e"j6        Z6e
e7e8ej9        ej:        ej        ej;        f         Z<e=e>         Z?ej@        e>ef         ZA ed          ZB G d d          ZC eC            ZDejE         G d de'                      Z& G d de jF                  ZFd ZG G d d          ZH G d dej@                  ZIejE         G d de.                      ZJejE         G d de.                      ZKejE         G d d eK                      ZLejE         G d! d"                      ZMejE         G d# d$                      ZNejE         G d% d&eK                      ZOejE         G d' d(eK                      ZP ejE        d)*           G d+ d,                      ZQejE         G d- d.                      ZRejE         G d/ d0                      ZSejE         G d1 d2eP                      ZT ejE        d)*           G d3 d4                      ZUejE         G d5 d6eP                      ZVejE         G d7 d8                      ZW ejE        d)*           G d9 d:                      ZX G d; d<          ZYdS )=zFunctionality to read and write metadata for CSV files.

This module implements (partially) the W3C recommendation
"Metadata Vocabulary for Tabular Data".

.. seealso:: https://www.w3.org/TR/tabular-metadata/
    N)OptionalUnionAnyLiteralTypeVar)Iterable	Generator)urljoinurlparse
urlunparse)tags   )utils	DATATYPES)DialectUnicodeReaderWithLineNumberUnicodeWriter)DataPackage)jsonld)DescriptionBasedataclass_asdict
NAMESPACESdialect_propsvalid_context_property)	
TableGroupTableColumn
ForeignKeyLinkNaturalLanguageDatatypeis_urlCSVWTc                       e Zd ZdS )InvalidN)__name__
__module____qualname__     Y/Users/jameslopez/projects/MentorCore/.venv/lib/python3.11/site-packages/csvw/metadata.pyr'   r'   8   s        Dr,   r'   c                   "    e Zd ZU dZdZeed<   dS )r   a  
    The spec is ambiguous regarding a default for the commentPrefix property:

    > commentPrefix
    >     An atomic property that sets the comment prefix flag to the single provided value, which
    >     MUST be a string. The default is "#".

    vs.

    > comment prefix
    >     A string that, when it appears at the beginning of a row, indicates that the row is a
    >     comment that should be associated as a rdfs:comment annotation to the table. This is set
    >     by the commentPrefix property of a dialect description. The default is null, which means
    >     no rows are treated as comments. A value other than null may mean that the source numbers
    >     of rows are different from their numbers.

    So, in order to pass the number formatting tests, with column names like `##.#`, we chose
    the second reading - i.e. by default no rows are treated as comments.
    NcommentPrefix)r(   r)   r*   __doc__r/   str__annotations__r+   r,   r-   r   r   ?   s.          & M3r,   r   c                   (     e Zd ZdZ fdZd Z xZS )URITemplatezAURITemplate properties support expansion, given suitable context.c                     t          |t                    r| j        |k    S t          |d          sdS t	                                          |          S )NuriF)
isinstancer1   r6   hasattrsuper__eq__)selfother	__class__s     r-   r:   zURITemplate.__eq__Y   sO    eS!! 	%8u$$ue$$ 	5ww~~e$$$r,   c                     |  S Nr+   r;   _s     r-   asdictzURITemplate.asdict`   s
    yr,   )r(   r)   r*   r0   r:   rB   __classcell__r=   s   @r-   r4   r4   W   sM        KK% % % % %      r,   r4   c                     | d S t          | t                    st          j        d           t          S t          |           S )NzInvalid value for Url property)r7   r1   warningswarnINVALIDr4   vs    r-   convert_uri_templaterK   d   s@    yta 6777q>>r,   c                       e Zd ZdZdeeej        f         fdZe	ded eej        f         fd            Z
d Zd Zd Zd	 Zd
S )r    zK

    .. seealso:: http://w3c.github.io/csvw/metadata/#link-properties
    stringc                 t    t          |t          t          j        f          st	          d          || _        d S )NzInvalid value for link property)r7   r1   pathlibPath
ValueErrorrM   )r;   rM   s     r-   __init__zLink.__init__s   s6    &3"566 	@>???r,   rJ   c                 F    t          |t                    r|S  | |          S r?   )r7   r    )clsrJ   s     r-   
from_valuezLink.from_valuex   s&    a 	Hs1vvr,   c                     | j         S r?   rM   r;   s    r-   __str__zLink.__str__~   s
    {r,   c                     | j         S )z=Not really a dict, but at least a JSON-serializable datatype.rW   r@   s     r-   rB   zLink.asdict   s
    {r,   c                 P    t          |t                    r| j        |j        k    ndS NF)r7   r    rM   r;   r<   s     r-   r:   zLink.__eq__   s'     /9.E.EPt{el**5Pr,   c                     t          |d          r@t          | j                  r| j        S |                                r|n|j        | j        z  S t          || j                  S )z
        Resolve a `Link` relative to `base`.

        :param base:
        :return: Either a string, representing a URL, or a `pathlib.Path` object, representing         a local file.
        joinpath)r8   r#   rM   is_dirparentr
   )r;   bases     r-   resolvezLink.resolve   sc     4$$ 	Jdk"" #{" KKMM:DDt{dkIItT[)))r,   N)r(   r)   r*   r0   r   r1   rO   rP   rR   classmethodrU   rY   rB   r:   rc   r+   r,   r-   r    r    m   s         
uS',%67    
 5gl!:;    [
    Q Q Q
* * * * *r,   r    c                        e Zd ZdZdeeee         ee         eeeeee         ee         f         f         f         f fdZ	d Z
ddedee         ddfd	Zdefd
Zddee         dee         fdZ xZS )r!   z
    A natural language property holds a collection of string, optionally categorized into languages.

    .. seealso:: http://w3c.github.io/csvw/metadata/#natural-language-properties
    valuec                 *   t                                                       || _        t          | j        t                    r| j        g| d <   d S t          | j        t
          t          f          rMt          d | j        D                       st          j	        d           d S t          | j                  | d <   d S t          | j        t                    r| j                                        D ]\  }}t          j        |          st          d          t          |t
          t          f          s|g}g }|D ]A}t          |t                    r|                    |           -t          j	        d           B|| |<   d S t          d          )Nc              3   @   K   | ]}t          |t                    V  d S r?   r7   r1   ).0rJ   s     r-   	<genexpr>z+NaturalLanguage.__init__.<locals>.<genexpr>   s,      >>az!S))>>>>>>r,   zAtitles with array values containing non-string values are ignoredz(Invalid language tag for NaturalLanguagez1Title with value which is not a string is ignoredz&invalid value type for NaturalLanguage)r9   rR   rf   r7   r1   listtupleallrF   rG   dictitemsr   checkrQ   append)r;   rf   krJ   titlesvvr=   s         r-   rR   zNaturalLanguage.__init__   s    	
dj#&& 	G*DJJJ
T5M22 	G>>4:>>>>> .abbbbb!$*--T



D)) 	G
((** ! !1z!}} Q$%OPPP!!dE]33 A [ [B!"c** [b)))) &YZZZZ Q! ! EFFFr,   c                     t          |           dgk    r5t          | d                   dk    r|                                 S | d         S t          j        d |                                 D                       S )zSerialize as dict.Nr   c              3   b   K   | ]*\  }}|dn|t          |          dk    r|d         n|fV  +d S )Nundr   r   len)rj   rs   rJ   s      r-   rk   z)NaturalLanguage.asdict.<locals>.<genexpr>   s]       '& '&1 iUUQA!!C'& '& '& '& '& '&r,   )rl   rz   getfirstcollectionsOrderedDictrp   r@   s     r-   rB   zNaturalLanguage.asdict   s{    ::$4:!##}}&:& '& '&

'& '& '& & & 	&r,   NrM   langreturnc                 N    || vrg | |<   | |                              |           dS )zAdd a string for a language.N)rr   )r;   rM   r~   s      r-   addzNaturalLanguage.add   s4    tDJT
&!!!!!r,   c                     |                                  p3t          t          |                                                     d         S Nr   )r{   nextitervaluesrX   s    r-   rY   zNaturalLanguage.__str__   s2    }}>$tDKKMM':':";";A">>r,   c                 <    |                      |dg          d         S )z=Return the first string specified for the given language tag.Nr   get)r;   r~   s     r-   r{   zNaturalLanguage.getfirst   s    xxtf%%a((r,   r?   )r(   r)   r*   r0   r   r1   rl   rm   ro   rR   rB   r   r   rY   r{   rC   rD   s   @r-   r!   r!      s        
Gd3isT#uS$s)UZ[^U_E_?`:`5aabG G G G G G8& & &" "# "Xc] "d " " " "? ? ? ? ?) )Xc] )hsm ) ) ) ) ) ) ) )r,   r!   c                      e Zd ZU dZdZeed<   dZee         ed<   dZ	ee
         ed<   dZee
         ed<   dZee
         ed<   dZeed<   dZeed	<   dZee         ed
<   dZee         ed<   dZee         ed<   dZee         ed<   d Zd Zd Zedeeed f         dd fd            ZddefdZedefd            Zedefd            Z de!defdZ"dede!fdZ#de$de$fdZ%dede!fdZ&dS )r"   a  
    A datatype description

        Cells within tables may be annotated with a datatype which indicates the type of the values
        obtained by parsing the string value of the cell.

    .. seealso:: `<https://www.w3.org/TR/tabular-metadata/#datatypes>`_
    Nrb   formatlength	minLength	maxLengthminimummaximumminInclusivemaxInclusiveminExclusivemaxExclusivec                      t          j        t          j        t          ddd           | j                  | _        |                                  |                                  d S )NrM   Tc                     | d u p| t           v S r?   r   )sss    r-   <lambda>z(Datatype.__post_init__.<locals>.<lambda>   s    B$J9"	/ r,   
allow_nonecond)	functoolspartialr   type_checkerr1   rb   _set_constraints_validate_constraintsrX   s    r-   __post_init__zDatatype.__post_init__   st    ;I%99; ; ;
 <@9F F	 	""$$$$$r,   c                     d } j         ; |d j        d uo j          j        k      j        d uo j          j        k                j        & j         j         j        k    rt          d          t	           j        t                    st                      t	                                           t          d dD                                 s' |dg fdd	                                D             R   t	                                           t          d	         t          d
         t          d         f          s |d j          j         j                    |d j        o j         j        o j                    |d j        o j        o j         j        k     j        o j        o j         j        k      j        o j        o j         j        k     j        o j        o j         j        k               d j        v r/t!           fdt          D                       rt          d          t	                                           t          d                   r`d j        v rYt#           j        d                                       t#          d                    s!d  _        t)          j        d           d S d S d S d S )Nc                 B    t          |          rt          |           d S r?   )anyrQ   )msg
conditionss     r-   error_ifz0Datatype._validate_constraints.<locals>.error_if   s&    : & oo%& &r,   zLength limits interferezminLength > maxLengthc              3   0   K   | ]}t           |         V  d S r?   r   )rj   names     r-   rk   z1Datatype._validate_constraints.<locals>.<genexpr>  s&      ``4y``````r,   )decimalfloatdatetimedurationzApplications MUST raise an error if minimum, minInclusive, maximum, maxInclusive, minExclusive, or maxExclusive are specified and the base datatype is not a numeric, date/time, or duration type.c                 0    g | ]}t          |          S r+   )getattr)rj   atr;   s     r-   
<listcomp>z2Datatype._validate_constraints.<locals>.<listcomp>  s5     c c c'$## c c cr,   zCminimum maximum minExclusive maxExclusive minInclusive maxInclusiverM   base64Binary	hexBinaryzApplications MUST raise an error if length, maxLength, or minLength are specified and the base datatype is not string or one of its subtypes, or a binary type.zApplications MUST raise an error if both minInclusive and minExclusive are specified, or if both maxInclusive and maxExclusive are specified.zLimits overlapidc              3   V   K   | ]#}j         d          t          d         |z   k    V  $dS )r   xsdN)at_propsr   )rj   dtr;   s     r-   rk   z1Datatype._validate_constraints.<locals>.<genexpr>'  sR       )S )SBDd#z%'82'==)S )S )S )S )S )Sr,   z8datatype @id MUST NOT be the URL of a built-in datatype.r   patternu   #0.,;%‰E-+zInvalid number pattern)r   r   r   rQ   r7   derived_descriptionro   basetyperm   splitr   r   r   r   r   r   r   setissubsetr   rF   rG   )r;   r   s   ` r-   r   zDatatype._validate_constraints   sl   	& 	& 	& ;"H)d*Kt{T^/Kd*Kt{T^/K   >%$.*DNT^334555$2D99 	,,``3_```aac c 	d HJdc c c cY__aac c c	d d d d 8$i&?;AWXZ Z 	= H T^T^	= = = 	Q3$"33$"3		
 	
 	
 	^$"3^8ITM^8^]$"3]8IDL]8]^$"3^8ITM^8^^$"3^8ITM^8^	
 	
 	
 4=  S )S )S )S )SHQ)S )S )S &S &S WXXXdmmooy';<< 	8T555t/	:;;DDSEXEXYY 8"677777		8 	8558 8r,   c                    dD ]A}t          | | t          j        t                    t	          | |                               BdD ]D}t	          | |          2t          | ||                     t	          | |                               Ed S )N)r   r   r   r   r   r   r   r   r   )setattrr   optcastintr   parse)r;   attattr_s      r-   r   zDatatype._set_constraints1  s    7 	G 	GCD#1u}S11'$2D2DEEFFFF
 	G 	GE tU##/eTZZe0D0D%E%EFFF		G 	Gr,   dr   c                    t          |t                    r | |          S t          |t                    r1|                    dd            | di |                     |          S t          ||           r|S t          |          )a   
        :param v: Initialization data for `cls`; either a single string that is the main datatype         of the values of the cell or a datatype description object, i.e. a `dict` or a `cls`         instance.
        :return: An instance of `cls`
        )rb   rb   rM   Nr+   )r7   r1   ro   
setdefaultpartition_propertiesrQ   rT   r   s     r-   	fromvaluezDatatype.fromvalue:  s     a 	3A;;;a 	6LL***35511!44555a 	Hmmr,   Tc                     t          j        | |          }dD ]$}||v r|                     ||                   ||<   %t          |          dk    rd|v r|d         S |S )z@The datatype serialized as dict suitable for conversion to JSON.omit_defaultsr   r   rb   )r   rB   	formattedrz   )r;   r   resr   s       r-   rB   zDatatype.asdictN  ss    $TGGG
 	8 	8E ||!^^CJ77E
s88q==Vs]]v;
r,   c                 &    t           | j                 S r?   )r   rb   rX   s    r-   r   zDatatype.basetypeZ  s    ##r,   c                 6    | j                             |           S r?   )r   r   rX   s    r-   r   zDatatype.derived_description^  s    }00666r,   rJ   c                 2     | j         j        |fi | j        S )zFormat a value as string.)r   	to_stringr   r;   rJ   s     r-   r   zDatatype.formattedb  s"    &t}&qEED,DEEEr,   c                 :    ||S  | j         j        |fi | j        S )z(Parse a string value into a Python type.)r   	to_pythonr   r   s     r-   r   zDatatype.parsef  s,    9H&t}&qEED,DEEEr,   c                 N   ||S 	 t          |pd          }| j        "|| j        k    rt          d| j                   | j        "|| j        k     rt          d| j                   | j        "|| j        k    rt          d| j                   n# t
          $ r Y nw xY w| j        j        r| j        "|| j        k     rt          d| j                   | j	        "|| j	        k     rt          d| j	                   | j
        "|| j
        k    rt          d| j
                   | j        "|| j        k    rt          d| j                   | j        "|| j        k    rt          d| j                   | j        "|| j        k    rt          d	| j                   |S )
z1Make sure the datatype-level constraints are met.N zvalue must have length z value must have at least length zvalue must have at most length zvalue must be >= zvalue must be > zvalue must be <= zvalue must be < )rz   r   rQ   r   r   	TypeErrorr   minmaxr   r   r   r   r   r   )r;   rJ   l_s      r-   validatezDatatype.validatel  s   9H		QW"B{&2+<+< !H4;!H!HIII~)b4>.A.A !TDN!T!TUUU~)b4>.A.A !S4>!S!STTT 	 	 	D	= 	I|'A,<,< !CT\!C!CDDD ,T5F1F1F !HT5F!H!HIII ,d6G1G1G !GD4E!G!GHHH|'A,<,< !CT\!C!CDDD ,T5F1F1F !HT5F!H!HIII ,d6G1G1G !GD4E!G!GHHHs   BB 
B B c                 R    |                      |                     |                    S )z3Read a value according to the spec of the Datatype.)r   r   r   s     r-   readzDatatype.read  s    }}TZZ]]+++r,   T)'r(   r)   r*   r0   rb   r1   r2   r   r   r   r   r   r   r   OrderedTyper   r   boolr   r   r   r   r   r   rd   r   ro   r   rB   propertytyper   r   r   r   r   r%   r   r   r+   r,   r-   r"   r"      s_          D# FHSM    FHSM   #Ix}####Ix}###G[G[#'L(4.'''#'L(4.'''#'L(4.'''#'L(4.'''% % %<8 <8 <8|G G G %T: 56 :    [&
 
D 
 
 
 
 $$ $ $ $ X$ 7T 7 7 7 X7F3 F3 F F F FFs Fs F F F F!     :,c ,c , , , , , ,r,   r"   c                      e Zd ZU dZdZee         ed<   dZee	e
ef                  ed<   dZee         ed<   dZee	eee         f                  ed<   dZeed	<    ej        d
           Zee         ed<   dZee         ed<   dZee	e
ef                  ed<   dZee         ed<   dZee         ed<   dZeed                  ed<   dZee	e
ef                  ed<   d Zdee         fdZdee         fdZ dS )DescriptionzvAdds support for inherited properties.

    .. seealso:: http://w3c.github.io/csvw/metadata/#inherited-properties
    N_parentaboutUrldatatyper   defaultrx   r~   c                      dgS )Nr   r+   r+   r,   r-   r   zDescription.<lambda>  s     r,   default_factorynullorderedpropertyUrlrequired	separator)ltrrtlautoinherittextDirectionvalueUrlc                 d   | j         $t                              | j                   | _         t          j        t
          d| j        d          | _        t          j        | j	                  st          j        d           d| _	        | j        g n(t          | j        t                    r| j        n| j        g| _        t          d | j        D                       st          j        d           dg| _        t          j        t           d| j        d	          | _        t          j        t
          d | j        d	          | _        t          j        t
          d | j        dd
           | _        dD ]>}t)          | |          ,t+          | |t-          t)          | |                               ?d S )Nr   F)
allow_listzInvalid language tagrx   c              3   @   K   | ]}t          |t                    V  d S r?   ri   )rj   ru   s     r-   rk   z,Description.__post_init__.<locals>.<genexpr>  s,      ;;2:b#&&;;;;;;r,   zInvalid null propertyTr   c                 
    | dv S )N)Nr   r   r   r   r+   rI   s    r-   r   z+Description.__post_init__.<locals>.<lambda>  s    1 GG r,   r   )r   r   r   )r   r"   r   r   r   r1   r   r   rq   r~   rF   rG   r   r7   rl   rn   r   r   r   r   r   r   rK   )r;   r   s     r-   r   zDescription.__post_init__  s   =$$..t}==DM)#r4<ERRRz$)$$ 	M0111DI)+BB$TY55FTYYDI; 		;;;;;;; 	M1222DI)$t|PTUUU+Ct~RVWWW"/GGI I I ; 	M 	MCtS!!-c#7c8J8J#K#KLLL	M 	Mr,   r   c                     t          | |          }|K| j        rDt          | j        d          r| j                            |          nt          | j        |          S |S )a  
        The implementation of the inheritance mechanism.

        The chain of inheritance is established by assigning a an object to `_parent`. If this
        object has a method `inherit` as well (i.e. is derived from Description), the chain
        may continue.
        Nr   )r   r   r8   r   )r;   attrrJ   s      r-   r   zDescription.inherit  s`     D$9918y1Q1Q 14<''---T\4001r,   c                     | j         dgk    r5| j        r.t          | j        d          r| j                                        S | j         S )zNInheritance of null is a special case due to the default value not being None.r   inherit_null)r   r   r8   r  rX   s    r-   r  zDescription.inherit_null  sJ    9| 3n E E 3|00222yr,   )!r(   r)   r*   r0   r   r   r   r2   r   r   r4   r'   r   r"   r   r1   rl   r~   dataclassesfieldr   r   r   r   r   r   r   r   r   r   r   r   r  r+   r,   r-   r   r     s          *.GXo&---6:Hhu['123:::#'Hhx '''/1GXeCcN+,111D#'k'EEED$s)EEE"GXd^"""9=K%W 456===#Hhtn####Ix}###48 8/02 9 9 96:Hhu['123:::M M M2x}    d3i      r,   r   c                        e Zd ZU dZdZeed<   dZeed<   dZ	e
e         ed<   dZeed<   dZe
e         ed<    fd	Zd
 Zd Zdeeef         fdZedefd            ZddedefdZdedefdZ xZS )r   a  
    A column description is an object that describes a single column.

        The description provides additional human-readable documentation for a column, as well as
        additional information that may be used to validate the cells within the column, create a
        user interface for data entry, or inform conversion into other formats.

    .. seealso:: `<https://www.w3.org/TR/tabular-metadata/#columns>`_
    Nr   FsuppressOutputrt   virtual_numberc                    t                                                       t          j        t          d | j        d          | _        t          j        t          d| j                  | _        | j        F	 t          | j                  | _        n+# t          $ r t          j        d           d | _        Y nw xY wt          j        t          d| j                  | _        d S )NTr   FzInvalid titles property)r9   r   r   r   r1   r   r   r  rt   r!   rQ   rF   rG   r  )r;   r=   s    r-   r   zColumn.__post_init__  s    &sD$)MMM	#0ud>QRR;"#-dk:: # # #7888"# )$t|DDs   6B %B87B8c                 d    | j         p)| j        r| j                                        p	d| j         S )N_col.)r   rt   r{   r  rX   s    r-   rY   zColumn.__str__  s6    y^T[CT[-A-A-C-C^H^PTP\H^H^^r,   c                 V    |                                  |                                 k    S r?   )rB   r]   s     r-   r:   zColumn.__eq__  s    {{}}..r,   r   c                     | j         r| j         |k    rdS | j        pi                                 D ]\  }}||v r|pdc S dS )z
        Check whether the name or a title of the column matches v.

        If v matches a title, the associated language tag (or 'und') is returned.
        Trx   F)r   rt   rp   )r;   rJ   tagrt   s       r-   	has_titlezColumn.has_title  sf     9 	a4 K-24466 	$ 	$KCF{{|e### ur,   c                     |  S r?   r+   rX   s    r-   headerzColumn.header	  s
    yr,   TrJ   c                    |                      d          }|                                 |                      d          |                      d          }|                      d          |s}|r)|v r%|st          j        d           t	          d          |r<|sg }n=|v rd}n6fd|                    |          D             }fd|D             }n|v rd}rbt          |t                    r8	 fd	|D             S # t          $ r |st          j        d
           |cY S  w xY w                    |          S |S )zFConvert a str to a Python object according to the spec for the column.r   r   r   r   z required column value is missingNc              3       K   | ]}|pV  	d S r?   r+   )rj   ru   r   s     r-   rk   zColumn.read.<locals>.<genexpr>#  s'      @@rR]7@@@@@@r,   c                      g | ]
}|v rd n|S r?   r+   )rj   ru   r   s     r-   r   zColumn.read.<locals>.<listcomp>$  s%    <<<BR4ZZTTR<<<r,   c                 :    g | ]}                     |          S r+   )r   )rj   ru   r   s     r-   r   zColumn.read.<locals>.<listcomp>+  s%    :::"HMM"--:::r,   zInvalid value for list element.)	r   r  rF   rG   rQ   r   r7   rl   r   )r;   rJ   strictr   r   r   r   r   s        @@@r-   r   zColumn.read  s   <<
++  "",,y))LL--	<<
++ 	A 	AT		 B@AAA?@@@ 		 =d@@@@QWWY-?-?@@@<<<<!<<<$YYA 		$!T"" ::::::::!   ! ! &GHHH 	
 ==###s   7D "D+)D+c                     |                      d          }|                                 |                      d          fd|r#|                    fd|pg D                       S  |          S )zEConvert v to a string according to the specifications for the column.r   r   c                 J    | d         S r                     |           S | S r   )r   )rJ   r   r   s    r-   fmtzColumn.write.<locals>.fmt:  s2    yAw -))!,,,Hr,   c              3   .   K   | ]} |          V  d S r?   r+   )rj   ru   r  s     r-   rk   zColumn.write.<locals>.<genexpr>B  s+      66CCGG666666r,   )r   r  join)r;   rJ   sepr   r  r   s      @@@r-   writezColumn.write4  s    ll;''  ""<<
++	 	 	 	 	 	  	7886666ag2666666s1vvr,   r   )r(   r)   r*   r0   r   r1   r2   r  r   rt   r   r!   r  r  r   r   rY   r:   r   r  r   r  r   r   r  rC   rD   s   @r-   r   r     sZ          D# ND   (,FH_%,,,GT!GXc]!!!E E E E E_ _ _/ / /eCI.         X% %c %3 % % % %Ns s        r,   r   c                   t    e Zd ZU dZdZee         ed<   dZee         ed<   dZ	ee
e                  ed<   d ZdS )	ReferencezJA reference specification as used to describe the targets of foreign keys.NresourceschemaReferencecolumnReferencec                 0   | j         :| j        t          |           t                              | j                   | _         | j        $t                              | j                  | _        t          | j        t                    r| j        g| _        d S d S r?   )r   r!  rQ   r    rU   r7   r"  r1   rX   s    r-   r   zReference.__post_init__M  s    =$#/ &&& OODM::DM+#'??43G#H#HD d*C00 	:$($8#9D   	: 	:r,   )r(   r)   r*   r0   r   r   r    r2   r!  r"  rl   r1   r   r+   r,   r-   r  r  F  sl         TT#Hhtn###&*OXd^***+/OXd3i(///: : : : :r,   r  c                       e Zd ZU dZdZeee                  ed<   dZ	ee
         ed<   d Zed             Zdeeef         fdZdS )	r   z!A specification of a foreign key.Nr"  	referencec                 X    t          | j        t                    r| j        g| _        d S d S r?   )r7   r"  r1   rX   s    r-   r   zForeignKey.__post_init__a  s5    d*C00 	:$($8#9D   	: 	:r,   c           	      t   t          |t                    r{	 t          di |d         }n"# t          $ r}t	          d          |d}~ww xY wt          |                                                              ddh          st	          d          t          |t          di |d                   } | di |S )zKInstantiate an object from a dict as returned by parsing the JSON metadata.r%  zInvalid reference propertyNr"  zInvalid foreignKey spec)r%  r+   )r7   ro   r  r   rQ   r   keysr   )rT   r   rA   ekws        r-   fromdictzForeignKey.fromdicte  s     a 	<F//+// F F F !=>>AEFqvvxx==))+<k*JKK < !:;;;!y::1[>::;;;syyRyys   * 
A	AA	r   c                 L    t          | fi |}t          |d         fi ||d<   |S )Nr%  )r   )r;   r*  r   s      r-   rB   zForeignKey.asdictr  s;    t**r**+C,<CCCCK
r,   )r(   r)   r*   r0   r"  r   rl   r1   r2   r%  r  r   rd   r+  ro   r   rB   r+   r,   r-   r   r   [  s         +++/OXd3i(///%)Ix	"))): : : 
 
 [
d38n      r,   r   c                       e Zd ZU dZ ej        e          Zee         e	d<    ej        e          Z
ee         e	d<   dZeee                  e	d<    ej        e          Zee         e	d<    fdZd	ed
ee         dee         defdZedeeef         dd fd            Zedeeef         fd            Zddededee         fdZ xZS )SchemaaL  
    A schema description is an object that encodes the information about a schema, which describes
    the structure of a table.

    :ivar columns: `list` of :class:`Column` descriptions.
    :ivar foreignKeys: `list` of :class:`ForeignKey` descriptions.

    .. seealso:: `<https://www.w3.org/TR/tabular-metadata/#schemas>`_
    r   columnsforeignKeysN
primaryKey	rowTitlesc           
      4   t                                                       d t          j        t          d t          j        t
          g | j                            D             | _        t          | j                  D ]\  }}|dz   |_        | j	        g | _	        n~g }t          j        t          d | j	                  D ]T}	 |
                    t                              |                     1# t          $ r t          j        d           Y Qw xY w|| _	        | j        't#          | j        t
                    s| j        g| _        t#          | j        t
                    r| j        n| j        g| _        dt'                      t'                      }}}t          | j                  D ]$\  }}|                     ||||          }| |_        %| j        pg D ]@}| j                            |          }|r"|j        st          j        d           d | _        Ad S )Nc                 B    g | ]}t                               |          S r+   r   r   rj   cs     r-   r   z(Schema.__post_init__.<locals>.<listcomp>  s9     X X X$%FQX X Xr,   r   zInvalid foreignKeys specFz:A primaryKey referenced column MUST have a `name` property)r9   r   r   r   ro   rl   r/  	enumerater  r0  rr   r   r+  r   rF   rG   r1  r7   r2  r   
_check_colr   
columndictr   r   )
r;   icolr   r   r  seennamescolrefr=   s
            r-   r   zSchema.__post_init__  s!   X XtT5+=dB+U+UVVX X X  -- 	  	 FAsa%CKK#!DC'dD4DEE > >>JJz221556666  > > >M"<=====>"D?&z$/4/P/P&#/DO+5dnd+K+KaRVR`Qa$ceeSUUu-- 	 	FAsooc7E4@@GCKKo+ 	' 	'F/%%f--C '38 'Z[[["&		' 	's   -C00DDr  r>  r=  r   c                    |j         rH|j                             d          st          j        d|j                   rt	          j        d           |j        rd}n|rt          d          |sx|j        |v rt	          j        d           |j         r:|j         |v rt          d|j                    |	                    |j                    |	                    |j                   |S )NrA   \szInvalid column nameTz3no non-virtual column allowed after virtual columnszDuplicate column name!zDuplicate column name )
r   
startswithresearchrF   rG   r  rQ   r  r   )r;   r<  r  r>  r=  s        r-   r9  zSchema._check_col  s    8 	1,,S11 	1RYuch5O5O 	1M/000; 	TGG 	TRSSS 	!zT!!6777x $8u$$$%Hch%H%HIII		#(###HHSZ   r,   r   c                 D   t          |t                    r1	 t          j        |                                          }n	#  |cY S xY wt          |t
                    s+t          |t                    rt          j        d           i } | di | 	                    |          S )z9Instantiate a Schema from a dict or a URL to a JSON file.z&Invalid value for tableSchema propertyr+   )
r7   r1   r   request_getjsonro   r   rF   rG   r   r   s     r-   r   zSchema.fromvalue  s     a 	%a((--//!T"" 	!S!! HFGGGAs11S--a00111s	   &> Ac                 $    d | j         D             S )z9A table's columns mapped by header, i.e. normalized name.c                     i | ]
}|j         |S r+   r  r6  s     r-   
<dictcomp>z%Schema.columndict.<locals>.<dictcomp>  s    222!222r,   )r/  rX   s    r-   r:  zSchema.columndict  s     32T\2222r,   Fr   r  c                    | j                             |          }|r|r|j        s
J |            |sM| j        D ]E}|j        r!|j                                        |k    r|c S |j        r|j        j        |k    r|c S F|S )z0Resolve a Column by name, titles or propertyUrl.)r:  r   r   r/  rt   r{   r   r6   )r;   r   r  r<  r7  s        r-   
get_columnzSchema.get_column  s    o!!$''77774771 	\  8  1 1 3 3t ; ;HHH= Q]%6$%>%>HHH
r,   F)r(   r)   r*   r0   r  r  rl   r/  r   r2   r0  r   r1  r   r1   r2  r   r   r   r9  rd   r   ro   r   r   r:  rM  rC   rD   s   @r-   r.  r.  x  s          .K-dCCCGT&\CCC$5K$5d$K$K$KKj!KKK&*Jc#***,;,TBBBItCyBBB' ' ' ' '@t CH CH QU    " 2%c	* 2x 2 2 2 [2 3Df- 3 3 3 X3
 
s 
D 
Xf=M 
 
 
 
 
 
 
 
r,   r.  c                   $    e Zd ZU dZdZeeeef                  e	d<    e
j        e          Zee         e	d<   dZed         e	d<   dZee         e	d	<    e
j        e          Zee	d
<   dZee         e	d<   dZeeej        f         e	d<    fdZdedee         fdZeddeeej        f         dd fd            Zeddedd fd            Zddeeej        f         dej        fdZedeeej        f         fd            Z dde!de"defdZ# xZ$S )	TableLikeaH  
    A CSVW description object as encountered "in the wild", i.e. identified by URL on the web or
    as file on disk.

    Since `TableLike` objects may be instantiated from "externally referenced" objects
    (via file paths or URLs), they have the necessary means to resolve
    `link properties <https://www.w3.org/TR/tabular-metadata/#link-properties>`_

    .. code-block:: python

        >>> from csvw import Table, TableGroup, Link
        >>> t = Table.from_file('tests/fixtures/csv.txt-table-metadata.json')
        >>> Link('abc.txt').resolve(t.base)
        PosixPath('tests/fixtures/abc.txt')
        >>> tg = TableGroup.from_url(
        ...     'https://raw.githubusercontent.com/cldf/csvw/master/tests/fixtures/'
        ...     'csv.txt-metadata.json')
        >>> str(tg.tables[0].url)
        'csv.txt'
        >>> tg.tables[0].url.resolve(tg.base)
        'https://raw.githubusercontent.com/cldf/csvw/master/tests/fixtures/csv.txt'

    and `URI template properties <https://www.w3.org/TR/tabular-metadata/#uri-template-properties>`_
    (see :meth:`~TableLike.expand`).
    Ndialectr   notesr   r   r   r   tableDirectiontableSchematransformationsurl_fnamec                    t                                                       t          | j        t                    r[t          d	i t          t          j        t          | j                  
                    | j                                      | _        n*| j        #t          d	i t          | j                  | _        t          j        t          d| j        d           | _        t                              | j                  | _        t          | j        t$                    st'          j        d           | j        D ]}t+          j        |d           | j        t          | j                  | _        | j        r&t          | j        t                    s| | j        _        d| j        v r| j        d         | j        | j        d<   t5          | j                            d                     d S )
Nr   c                 
    | dv S )NrS  r+   )ss    r-   r   z)TableLike.__post_init__.<locals>.<lambda>  s    QBX=X r,   )r   z Invalid transformations propertyTemplate)	type_namer   contextr+   )r9   r   r7   rQ  r1   r   r   r   get_jsonr    rc   rb   r   rT  r.  r   rU  rV  rl   rF   rG   r   r   rW  r   r   r   r   )r;   trr=   s     r-   r   zTableLike.__post_init__  s   dlC(( 	B" X XtDL/A/A/I/I$)/T/T U UVVX XDLL\%"AA]4<%@%@AADL#0,3X3XZ Z Z!++D,<==$.55 	>M<===& 	K 	KB0zJJJJJ8DH~~DH 	,Jt/?$E$E 	,'+D$4=  T]4%8%@"&)DM$t}00;;<<<<<r,   specr   c                 H    | j         r| j                             |          nd S r?   rU  rM  )r;   ra  s     r-   rM  zTableLike.get_column  s&    484DNt**4000$Nr,   fnamec                 
   t          t          |                    r$|                     t          |          |          S |                     |pt	          j        |                    }t          j        |          |_        |S )zZ
        Instantiate a CSVW Table or TableGroup description from a metadata file.
        data)	r#   r1   from_urlr   r   r_  rO   rP   rX  )rT   rd  rg  r   s       r-   	from_filezTableLike.from_file  sl    
 #e** 	7<<E

<666mmD9EN5$9$9::\%((

r,   c                    |pt          j        |          }t          |          }|                    dt	          |j        |j        |j        dddf                     |                    d|g          D ]p}t          |t                    rYt          |                    d          t                    r1t          |d                                       |d                   |d<   q|                     |          }|S )zk
        Instantiate a CSVW Table or TableGroup description from a metadata file specified by URL.
        @baser   tablesrU  )r   r_  r   r   r   schemenetlocpathr   r7   ro   r1   r    rc   r   )rT   rW  rg  tabler   s        r-   rh  zTableLike.from_url$  s    
 *u~c**smmSZSXrSUWY,Z![![\\\XXh// 	Y 	YE%&& Y:eii6N6NPS+T+T Y'+E-,@'A'A'I'I$w-'X'Xm$mmD!!
r,   Tc                     t          j        |          }|                     |          }t          j        t          |          d          5 }t          j        ||dd           ddd           n# 1 swxY w Y   |S )a/  
        Write a CSVW Table or TableGroup description as JSON object to a local file.

        :param omit_defaults: The CSVW spec specifies defaults for most properties of most         description objects. If `omit_defaults==True`, these properties will be pruned from         the JSON object.
        r   w   ),: )indent
separatorsN)rO   rP   rB   r   	json_openr1   rG  dump)r;   rd  r   rg  fs        r-   to_filezTableLike.to_file2  s     U##{{{77_SZZ-- 	AIdAaK@@@@	A 	A 	A 	A 	A 	A 	A 	A 	A 	A 	A 	A 	A 	A 	As   A22A69A6c                    | j         r| j         j        n| j        }d}| j                            dg           D ]#}t          |t                    rd|v r|d         }$d|v r2|r(t          |                              |d                   S |d         S | j         r| j         j        r| j         j        j        S | j        r| j        j        ndS )z?
        The "base" to resolve relative links against.
        Nr^  rk  rb   )	r   r   r   r7   ro   r    rc   rX  ra   )r;   r   ctxbaseobjs       r-   rb   zTableLike.base@  s    
 -1LK4<((dm=$$Y33 	' 	'C#t$$ 'Cg,X ? G}},,Xf-=>>>F##< 	.DL/ 	.<&--%)[:t{!!d:r,   Ftmplrowc           	         |t           u r| j                            | j                  S t	          j                    D ]H\  }}|j                            |dz             r&| |j                            d          d          } nxIt           |j
        d||dd |                                D                                           | j        r| j                            | j                  n| j                  }t          |t          j                  sK|rIt	          j                    D ]5\  }}|                    |          r|                    ||dz             } n6|S )a#  
        Expand a `URITemplate` using `row`, `_row` and `_name` as context and resolving the result
        against `TableLike.url`.

        .. code-block:: python

            >>> from csvw import URITemplate, TableGroup
            >>> tg = TableGroup.from_url(
            ...     'https://raw.githubusercontent.com/cldf/csvw/master/tests/fixtures/'
            ...     'csv.txt-metadata.json')
            >>> tg.expand(URITemplate('/path?{a}{#b}'), dict(a='1', b='2'), None)
            'https://raw.githubusercontent.com/path?1#2'

        :r   )_row_namec                 D    i | ]\  }}t          |t                    ||S r+   ri   )rj   _k_vs      r-   rK  z$TableLike.expand.<locals>.<dictcomp>r  s-    OOO&"b:b#;N;NOr2OOOr,   r+   )rH   rW  rc   rb   r   rp   r6   rB  r   r    expandr7   rO   rP   replace)	r;   r  r  r  r  qnameprefixrW  r   s	            r-   r  zTableLike.expandU  s    7??8##DI...%+-- 	S 	SKFCx""6C<00  6dhnnS11!466	    POCIIKKOOO  
 7$(Q48++DI666	RR  #w|,, 	 #-#3#5#5  KFC~~c** !kk#v|<< 
r,   r?   r   r\   )%r(   r)   r*   r0   rQ  r   r   r1   r   r2   r  r  rl   rR  rT  r   rU  r.  rV  rW  r    rX  rO   rP   r   r   rM  rd   ri  rh  r{  r   rb   r4   ro   r  rC   rD   s   @r-   rP  rP    s9         2 .2GXeCL)*111({(>>>E49>>>4:NG01:::$(K&!(((-K-dCCCOTCCCC$'+FE#w|#$+++= = = = =2Os Ox'7 O O O O  eC$56 k    [  3 k    [ U3#45 gl     ;eC-. ; ; ; X;(% %; %T %UX % % % % % % % %r,   rP  T)frozenc                   >    e Zd ZU dZeed<   eed<   ee         ed<   dS )CsvRowz3A bag of attributes specifying a row in a CSV file.rd  linenor  N)r(   r)   r*   r0   r1   r2   r   rl   r+   r,   r-   r  r  }  s5         ==JJJKKK	cNNNNNr,   r  c                   p    e Zd ZU dZeed<   eej                 ed<   e	j
        Zeed<   dZeed<   defdZd	S )
RowParseSpecz0A bag of attributes used when parsing a CSV row.r  logrow_implementationFerrorr   c                 J    t          j        || j                   d| _        dS )zLog and record error.r  TN)r   log_or_raiser  r  )r;   r   s     r-   	log_errorzRowParseSpec.log_error  s%    3DH----


r,   N)r(   r)   r*   r0   r   r2   r   loggingLoggerr|   r}   r  r   r  r1   r  r+   r,   r-   r  r    sw         ::LLL	'.	!!!!*6666E4S      r,   r  c                       e Zd ZU dZ ej        e          Zee         e	d<    ej        e          Z
eeeef                  e	d<    ej        e          Zee         e	d<   edee         dd fd            Zd	S )
TableParseSpecz/Some metadata, categorizing columns in a table.r   colnamesvirtualcolsrequiredcolsr/  r   c                     |             }|D ]|}|j         r.|j        r&|j                            |j        |j        f           n|j                            |j                   |j        r|j                            |j                   }|S )z:Initialize from columns (e.g. columns property of Schema).)	r  r   r  rr   r  r  r   r  r   )rT   r/  r   r<  s       r-   from_columnszTableParseSpec.from_columns  s     cee 	1 	1C{ 0< GO**CJ+EFFF##CJ///| 1 $$SZ000
r,   N)r(   r)   r*   r0   r  r  rl   r  r1   r2   r  rm   r4   r   r  rd   r   r   r  r+   r,   r-   r  r    s         99+++DAAAHd3iAAA1B1BSW1X1X1XKeC,-.XXX.[.sCCCL#c(CCC8F#3 8H    [  r,   r  c                      e Zd ZU dZdZeed<   g Zd Zd Z	e
deedf         fd            Zdefd	Zedddfd
eeeeef                  deeeej        f                  deeeej        f                  dee         dee         deeef         fdZd!defdZd ZdefdZdee         fdZdede deeeee!f                  de"de#f
dZ$dee         dee         dededeeeee!f                  f
dZ%ddde&j'        dfdee(j)                 dede*de+eeee,f         eeeeee,f         f         f         ddf         fd Z-dS )"r   a  
    A table description is an object that describes a table within a CSV file.

    `Table` objects provide access to schema manipulation either by manipulating the `tableSchema`
    property directly or via higher-level methods like :meth:`~Table.add_foreign_key`

    `Table` objects also mediate read/write access to the actual data through

    - :meth:`~Table.write`
    - :meth:`~Table.iterdicts`

    .. seealso:: `<https://www.w3.org/TR/tabular-metadata/#tables>`_
    Fr  c                     t          |t          t          f          s|gn|}t           fd|D                       st	          d|            j        j                            t          	                    |||dd                     dS )a	  
        Add a foreign key constraint to `tableSchema.foreignKeys`.

        :param colref: Column reference for the foreign key.
        :param ref_resource: Referenced table.
        :param ref_colref: Column reference of the key in the referenced table.
        c              3   H   K   | ]}|d  j         j        D             v V  dS )c                     g | ]	}|j         
S r+   )r   r6  s     r-   r   z3Table.add_foreign_key.<locals>.<genexpr>.<listcomp>  s    DDDa16DDDr,   N)rU  r/  )rj   r<  r;   s     r-   rk   z(Table.add_foreign_key.<locals>.<genexpr>  s=      WW3DD4+;+CDDDDWWWWWWr,   zunknown column in foreignKey )r   r"  )r"  r%  N)
r7   rm   rl   rn   rQ   rU  r0  rr   r   r+  )r;   r?  ref_resource
ref_colrefs   `   r-   add_foreign_keyzTable.add_foreign_key  s     ",FUDM!B!BN&WWWWPVWWWWW 	GEVEEFFF$++J,?,?%&2zRRA
 A
 - - 	 	 	 	 	r,   c                 f    t                               |            | j        st          d          d S )Nz#url property is required for Tables)rP  r   rW  rQ   rX   s    r-   r   zTable.__post_init__  s<    %%%x 	DBCCC	D 	Dr,   r   Nc                 ,    | j         r| j         j        ndS )zThe filename of a table.N)rW  rM   rX   s    r-   
local_namezTable.local_name  s     #'(4tx4r,   c                 R    | j         p | j        r| j        j         pt                      S r?   )rQ  r   r   rX   s    r-   _get_dialectzTable._get_dialect  s$    |S E1ES'))Sr,   rp   rd  rb   r  _zippedc                    |                                  }d | j        j        D             }|t          u r5| j                            |rt          j        |          n| j                  }d}t          ||          5 }	|j
        r|	                    d |D                        |D ]Ŋt          t          t          f          rfdt          |          D             }
nq|rat!                                                    d |D             z
  }|r1d                    d |D                       }t'          d	|           fd
|D             }
|dz  }|	                    |
           | |	                                cddd           S 	 ddd           n# 1 swxY w Y   |r|rt          j        |          }t+          j        t/          |j                            |j        dz                       dt*          j                  5 }|                    t/          |          |j                   ddd           n# 1 swxY w Y   |                                 |S )a  
        Write row items to a CSV file according to the table schema.

        :param items: Iterator of `dict` storing the data per row.
        :param fname: Name of the file to which to write the data.
        :param base: Base directory relative to which to interpret table urls.
        :param strict: Flag signaling to use strict mode when writing. This will raise `ValueError`        if any row (dict) passed in `items` contains unspecified fieldnames.
        :param _zipped: Flag signaling whether the resulting data file should be zipped.
        :return: The CSV content if `fname==None` else the number of rows written.
        c                      g | ]}|j         	|S r+   )r  r6  s     r-   r   zTable.write.<locals>.<listcomp>  s    QQQ!qyQAQQQr,   r   rQ  c                     g | ]	}|j         
S r+   rJ  r6  s     r-   r   zTable.write.<locals>.<listcomp>  s     D D Da D D Dr,   c                 L    g | ] \  }}|                     |                   !S r+   )r  )rj   r;  r<  items      r-   r   zTable.write.<locals>.<listcomp>  s-    XXX&!S399T!W--XXXr,   c                     h | ]}| S r+   r+   rj   r<  s     r-   	<setcomp>zTable.write.<locals>.<setcomp>  s    1W1W1WsS(1W1W1Wr,   z, c              3   "   K   | ]
}d | d V  dS )'Nr+   )rj   r  s     r-   rk   zTable.write.<locals>.<genexpr>  s*      +J+JULLLL+J+J+J+J+J+Jr,   z(dict contains fields not in fieldnames: c           
          g | ]D}|                                         |j                            |                               ES r+   )r  r   r  )rj   r<  r  s     r-   r   zTable.write.<locals>.<listcomp>  sS     5 5 5 		$((3:txx37I7I"J"JKK5 5 5r,   r   N.ziprr  )compression)arcname)r  rU  r/  DEFAULTrW  rc   rO   rP   rb   r   r  writerowr7   rl   rm   r8  r   r(  r  rQ   r   zipfileZipFiler1   ra   r_   r   ZIP_DEFLATEDr  unlink)r;   rp   rd  rb   r  r  rQ  non_virtual_colsrowcountwriterr  r   fpathzipfr  s                 @r-   r  zTable.write  s(   " ##%%QQt'7'?QQQGH$$4%NW\$%7%7%7TYOOE5'222 	%f~ F D D3C D D DEEE % %dT5M22 
5XXXXIFV<W<WXXXCC _!$))++..1W1WFV1W1W1WW _"&))+J+Jc+J+J+J"J"JC",-]X[-]-]"^"^^5 5 5 5#35 5 5C A$$$$}{{}}%	% 	% 	% 	% 	% 	% 	% 	%" #	% 	% 	% 	% 	% 	% 	% 	% 	% 	% 	% 	% 	% 	% 	%&  	W 	L''EEL))%*v*=>>??#0   ; 

3u::uz
:::; ; ; ; ; ; ; ; ; ; ; ; ; ; ; LLNNNs%   =DFF"F*II	Ic                    t          j        t                    }|                    t          j                               d}|t          j        d           | j        j        rt          j
        | j        j         }t                      }|                     |d          D ]K\  }}}	 ||	          }
|
|v r!t          j        | d| d|
 |           d}6|                    |
           L|S )	z"Make sure primary keys are unique.TNzSthe items argument of check_primary_key is deprecated (its content will be ignored)r  with_metadatar  z duplicate primary key: r  F)r  	getLoggerr(   
addHandlerNullHandlerrF   rG   rU  r1  operator
itemgetterr   	iterdictsr   r  r   )r;   r  rp   nologsuccessget_pkr=  rd  r  r  pks              r-   check_primary_keyzTable.check_primary_key  s
    !(++,..///M H I I I& 
	!($*:*EFF55D&*nndn&S&S ! !"vsVC[[::&%'V'V&'V'VRT'V'V\_````#GGHHRLLLLr,   c                 *    |                                  S r?   )r  rX   s    r-   __iter__zTable.__iter__&  s    ~~r,   c           	         t          |          rRt          j        t          j        t	          j        t          |                    j                  |j                  }n|}t          j
        |                                          sj                            j        dz             }|                                ry|                    t!          j        |                    }t          j        |                    fd|                                D             d                   |j                  }|                    t)          ||                    S )N)encodingr  c                 H    g | ]}|                     j                  |S r+   )endswithr   )rj   nr  s     r-   r   z)Table._get_csv_reader.<locals>.<listcomp>5  s,    "X"X"XEJAWAW"X1"X"X"Xr,   r   r  )r#   ioTextIOWrapperBytesIOr   rF  r1   contentr  rO   rP   existsra   r_   r   enter_contextr  r  opennamelistr   )r;   rd  rQ  stackhandlezipfnamer  r  s          @r-   _get_csv_readerzTable._get_csv_reader)  s7   %== 	3%
5,SZZ88@AAGL\^ ^ ^FF FL''E<<>> 3 <00f1DEE??$$ 3 ..wx/H/HIID-		"X"X"X"Xdmmoo"X"X"XYZ"[\\!(!13 3 3F ""#>vw#W#W#WXXXr,   c                    |s| j         j        r>t          | j         j                  t          |          k     rt          j        d           t          || j         j                  D ]\  }}|                    |          }|j        s|st          j        d           t          |t                    rS|
                    d          d         d| j        pd
                    d          d         fvrt          j        d           |S )NzColumn number mismatchzIncompatible table models-r   rx   zIncompatible column titles)rU  r/  rz   rF   rG   zipr  r   r7   r1   r   r~   )r;   r  r  r   r<  r   s         r-   _validated_csv_headerzTable._validated_csv_header:  s    		@' 8C0@0H,I,ICPVKK,W,W6777 )9)ABB @ @	cmmD)) ?# ?M"=>>>sC(( @		#q)%$):Lu9S9STW9X9XYZ9[1\\\M">???r,   r  
parse_specheader_colsra  c                 B   d |D             }|                                 }t          ||j                  D ]\  \  }}}	}
|	r	 |	                    |
|j                  ||	j        <   n{# t          $ rn}|j        s-t          j        d|
 d|	j	         d|            |
||	j        <   n0|
                    |j         d|j         d|dz    d| d| 	           Y d }~nd }~ww xY w||v r||= |j        rt          j        d	| d
| j                    |
||<   |                                D ]7\  }}||vr.|
                    |j         d|j         d|dz    d| d           8|j        D ]}|                    |d            |j        D ]\  }} |j        di |||<   |S )Nc                 .    i | ]\  }}}||j         ||S r+   )r   rj   jhr7  s       r-   rK  z#Table._read_row.<locals>.<dictcomp>N  s,    HHHWQ1qHQZHAqHHHr,   r  zInvalid column value:  z; r  r   ru  zUnspecified column "z" in table z": required column value is missingr+   )r  r  r  r   r  r  rQ   rF   rG   r   r  rd  r  r  rp   r  r   r  r  )r;   r  r  r  ra  r   r   r  rs   r<  rJ   r)  key	value_urls                 r-   	_read_rowzTable._read_rowG  sO    IHHHH++--!+sw77 	 	NKQ3 [&)hhq9Jh&K&KC
OO! [ [ [%, [ &Vq&V&V3<&V&VST&V&VWWW*+CJ",,	-Y-YCJ-Y-YQ-Y-YQR-Y-YVW-Y-YZZZ[ == $ ZM"X"X"Xt"X"XYYYANN$$ 	_ 	_DAq||$$y]]3:]]A]]]]]_ _ _ = 	& 	&CNN3%%%% #. 	/ 	/NC'y'..#..CHH
s   $A''
C1A$CCr  r  c                     d }||k    s,t           j        j                  t          |          k    r*|s(t          t	          | j        j                            }n|s j        j        rt           j        j                  t          |          k     rzg }t          |          D ]g\  }}	 |                    | j        j        |         f           .# t          $ r-  ||dz             }	|                    |	j        |	f           Y dw xY wn fd|D             }|s?t          |          D ]/\  }}
 ||dz             }	|                    |	j        |	f           0d t          |          D             S )Nc                 @    t                               dd|  i          S )Nr   r  r5  )indexs    r-   default_colz+Table._get_header_cols.<locals>.default_colx  s!    ##V_U__$=>>>r,   r   c                 H    g | ]}|j                             |          fS r+   rc  )rj   r  r;   s     r-   r   z*Table._get_header_cols.<locals>.<listcomp>  s/    OOO1At/::1==>OOOr,   c                 $    g | ]\  }\  }}|||fS r+   r+   r  s       r-   r   z*Table._get_header_cols.<locals>.<listcomp>  s&    BBBia!QAq	BBBr,   )	rz   rU  r/  rl   r  r8  rr   
IndexErrorr   )r;   r  r  r  r  r  r  r;  cnamer<  rA   s   `          r-   _get_header_colszTable._get_header_colsq  s   	? 	? 	?
 hT%-..#f++==f= s64+;+CDDEEKK 
	PD,4 
	PT%-..V<<K%f-- 8 858&&t/?/G/J'KLLLL! 8 8 8%+a!e,,C&&#7777788 POOOOOOK 	4!# 4 41!k!a%((""CHc?3333BB9[+A+ABBBBs   .'C4DDTr  r  _Rowc           	   #     K   |                                  }|p| j                            | j                  }t                              | j        j                  }t          j	                    5 }t          |                     |||                    }	|j        rG	 |                     t          |	          d         |          }
n## t          $ r Y ddd           dS w xY w|j        }
d}t#          |	          D ]\  }\  }}|dk    rG|                     |
|j        ||          }|j        d |D             z
  }|rt)          | d|           t+          |||          }|                     t/          |||          |||          }|j        s|r|||fn|V  	 ddd           n# 1 swxY w Y   |	j        | _        dS )a$  Iterate over the rows of the table

        Create an iterator that maps the information in each row to a `dict` whose keys are
        the column names of the table and whose values are the values in the corresponding
        table cells, or for virtual columns (which have no values) the valueUrl for that
        column. This includes columns not specified in the table specification.

        Note: If the resolved data filename does not exist - but there is a zip file of the form
        `fname+'.zip'`, we try to read the data from this file after unzipping.

        :param log: Logger object (default None) The object that reports parsing errors.        If none is given, parsing errors raise ValueError instead.
        :param bool with_metadata: (default False) Also yield fname and lineno
        :param fname: file-like, pathlib.Path, or str (default None)        The file to be read. Defaults to inheriting from a parent object, if one exists.
        :param strict: Flag signaling whether data is read strictly - i.e. raising `ValueError`         when invalid data is encountered - or not - i.e. only issueing a warning and returning         invalid data as `str` as provided by the undelying DSV reader.
        :return: A generator of dicts or triples (fname, lineno, dict) if with_metadata
        r   Nr   c                 (    h | ]\  }}}||j         S r+   rJ  r  s       r-   r  z"Table.iterdicts.<locals>.<setcomp>  s%    BBBgaABBBBr,   z is missing required columns )r  r  r  )rd  r  r  )r  rW  rc   rb   r  r  rU  r/  
contextlib	ExitStackr   r  r  r  r   StopIterationr  r8  r  r  rQ   r  r  r  r  comments	_comments)r;   r  r  rd  r  r  rQ  table_parse_specr  readerr  r  r;  r  r  missingr  r   s                     r-   r  zTable.iterdicts  s     8 ##%%4))$)44)66t7G7OPP!## 	Iu$..uguEEFFF ~ 3!77VQPPFF$   	I 	I 	I 	I 	I 	I 	I 	I *2K$-f$5$5 I I =FC66"&"7"7 0 963#H #HK.;BBBBBCG [(E)Y)YPW)Y)YZZZ)SUYZZZ
nnv3???$	  "' I2?H5&#..SHHH#I	I 	I 	I 	I 	I 	I 	I 	I 	I 	I 	I 	I 	I 	I 	I@  s7   /,F))CF)
CF)CB=F))F-0F-)NN).r(   r)   r*   r0   r  r   r2   r
  r  r   r   r   r1   r  r   r  r  r   ro   rl   rm   r   rO   rP   r   r  r  r  r   r  r  r  r  r   r  RowTyper  r  r|   r}   r  r  r   r	   r   r  r+   r,   r-   r   r     s          !ND   I  "D D D
 5E#t), 5 5 5 X5Tg T T T T
 ;B9=',(-3 3eD$$5673eC$5673 U3#4563 tn	3
  ~3
 38S/3 3 3 3j     0     Y8S Y Y Y Y"tCy    (( %( eCf$456	(
 !( 
( ( ( (T#CI#C 3i#C 	#C
 #C 
eCf$%	&#C #C #C #CN -1"'$0A) A)'.)A)  A)
 A) 
5c3hsCc3h/G)HHI4QUU	VA) A) A) A) A) A)r,   r   c                   L    e Zd ZU dZeed<   eed<   eed<   eed<   deddfd	ZdS )
ForeignKeyInstancez<Simple structure holding the specification of a foreign key.target_tabler  source_tablefkr  r   Nc                     t          | j                  t          | j                  k    rt          d          t	          | j        | j                  D ]\  }}| j        j                            ||          }| j        j                            ||          }|r|st          d| d| d          |j	        rQ|j	        rJ|j	        j
        |j	        j
        k    r0t          d| d|j	        j
         d| d|j	        j
         d	          dS )	z/Checks whether the colrefs for fk and pk match.zFForeign key error: non-matching number of columns in source and targetr  #Foreign key error: missing column "z" or ""z*Foregin key error: non-matching datatype "r  N)rz   r  r  rQ   r  r  rU  rM  r  r   rb   )r;   r  scoltcolscolumntcolumns         r-   r   zForeignKeyInstance.validate  s_   tw<<3tw<<''XZ Z Zdgtw// 
	< 
	<JD$'3>>tF>SSG'3>>tF>SSG O O M$MMdMMMO O O <G$4 <$)W-=-BBB ; ; ;HXH] ; ;; ;")"2"7; ; ;< < <
	< 
	<r,   )	r(   r)   r*   r0   r   r2   
ColRefTyper   r   r+   r,   r-   r  r    sh         FFNNNNNN<t < < < < < < <r,   r  c                       e Zd ZU dZ ej        e          Zee         e	d<    fdZ
ed             Zd Z	 	 ddeeej        f         d	ee         d
ee         deeeeef                  fdZdeej        ef         fdZedeeef         fd            Zdd	edee         fdZddZedededej         e!eeee!f                  f         d	ede"j#        defd            Z$ xZ%S )r   aM  
    A table group description is an object that describes a group of tables.

    A `TableGroup` delegates most of its responsibilities to the `Table` objects listed in its
    `tables` property. For convenience, `TableGroup` provides methods to
    - read data from all tables: :meth:`TableGroup.read`
    - write data for all tables: :meth:`TableGroup.write`

    It also provides a method to check the referential integrity of data in related tables via
    :meth:`TableGroup.check_referential_integrity`

    .. seealso:: `<https://www.w3.org/TR/tabular-metadata/#table-groups>`_
    r   rl  c                 z   g }| j         D ]w}t          |t          t          f          st	          j        d           3|                    t          |t                    rt                              |          n|           x|| _         t                      	                                 | j         D ]	}| |_
        
d S )NzInvalid value for Table spec)rl  r7   ro   r   rF   rG   rr   r   r9   r   r   )r;   r   ru   rp  r=   s       r-   r   zTableGroup.__post_init__  s    + 	P 	PBb4-00 P<====

*R2F2FN5??2...BOOOO[ 	! 	!E EMM	! 	!r,   c                 F    t          |                              |           S )z8Initialize a TableGroup from a frictionless DataPackage.)r   to_tablegroup)rT   dps     r-   from_frictionless_datapackagez(TableGroup.from_frictionless_datapackage  s     2,,S111r,   c                 H    d | j                                         D             S )z/
        Read all data of a TableGroup
        c                 X    i | ]'\  }}|t          |                                          (S r+   )rl   r  )rj   tnamets      r-   rK  z#TableGroup.read.<locals>.<dictcomp>  s.    RRRxuatAKKMM**RRRr,   )	tabledictrp   rX   s    r-   r   zTableGroup.read  s'     SR4>;O;O;Q;QRRRRr,   Frd  r  r  rp   c                     t          j        |          }|                                D ].\  }}| j        |                             ||j        ||           /|                     |           dS )a  
        Write a TableGroup's data and metadata to files.

        :param fname: Filename for the metadata file.
        :param items: Keyword arguments are used to pass iterables of rows per table, where the         table URL is specified as keyword.
        )rb   r  r  N)rO   rP   rp   r&  r  ra   r{  )r;   rd  r  r  rp   r$  rowss          r-   r  zTableGroup.write  sr     U## ;;== 	a 	aKE4N5!''5<X_'````Ur,   destc           	      f   t          j        |          }| j        D ]f}t          j        t          |j                            | j                            t          |j                            |                               g|| j	        j
        z  | _	        |                     | j	                   dS )z
        Write a TableGroup's data and metadata to files relative to `dest`, adapting the `base`
        attribute.

        :param dest:
        :return:
        N)rO   rP   rl  shutilcopyr1   rW  rc   rb   rX  r   r{  )r;   r)  rp  s      r-   r,  zTableGroup.copy-  s     |D!![ 	Y 	YEKEI--di88993uy?P?PQU?V?V;W;WXXXXT[--T[!!!!!r,   r   c                 $    d | j         D             S )z$Convenient access to tables by name.c                     i | ]
}|j         |S r+   )r  rj   r%  s     r-   rK  z(TableGroup.tabledict.<locals>.<dictcomp>>  s    555Aa555r,   )rl  rX   s    r-   r&  zTableGroup.tabledict;  s     655555r,   c                 $    	 t           fd j        D             d           }n&# t          $ r}t          d| d          |d}~ww xY w	 |D ]}|                    |           n&# t
          $ r}t          d| d          |d}~ww xY w|S )	z?Check whether pk and fk specs in foreign key constraints match.c                     g | ]r}|j         j        D ]c}|j        j        t	          j        |j        j        j                 t          |j        j	                  |t          |j	                            dsS r+   )
rU  r0  r%  r!  r  r&  r   rM   rm   r"  )rj   r%  r  r;   s      r-   r   z.TableGroup.validate_schema.<locals>.<listcomp>D  s     9 9 9 1=3L9 9 .0<79&r|'<'CDbl:;;b011	3 39 9 9 9r,   c                 >    | j         j        | j        | j        j        fS r?   )r  r  r  r  xs    r-   r   z,TableGroup.validate_schema.<locals>.<lambda>L  s    q~8!$@YZ r,   )r  z"Foreign key error: missing table "z" referencedNr  r  )sortedrl  KeyErrorrQ   r   AssertionError)r;   r  fkisr)  fkis   `    r-   validate_schemazTableGroup.validate_schema@  s   	Z9 9 9 9 "[9 9 9 [Z	\ 	\ 	\DD  	Z 	Z 	ZQ!QQQRRXYY	Z	[ , ,F++++, 	[ 	[ 	[R1RRRSSYZZ	[s,   #' 
A
AA
A* *
B4BBNc           	         |t          j        d           |ri| j        D ]a}|j        j        D ]R}|D ]Mt          fd|j        D                       r+t          dfd|j        D              d|j                   NSb	 |                                 }d}n?# t          $ r2}g }d}t          j
        t          |          |d	
           Y d}~nd}~ww xY wt          j        |d           D ]\  }	}
t          |
          }
|
d         j        }t!          j                    }t          j        |
d           D ]!\  }}d |D             |t%          |          <   "|                     |||||          }|S )zT
        Strict validation does not allow for nullable foreign key columns.
        Nz\the data argument of check_referential_integrity is deprecated (its content will be ignored)c              3   F   K   | ]}                     |          d u V  d S r?   r   rj   r<  r  s     r-   rk   z9TableGroup.check_referential_integrity.<locals>.<genexpr>a  s2      RRswws||t3RRRRRRr,   zForeign key column is null: c                 :    g | ]}                     |          S r+   r   r=  s     r-   r   z:TableGroup.check_referential_integrity.<locals>.<listcomp>d  s#    #O#O#OSCGGCLL#O#O#Or,   r  TFr  )r  levelc                     | j         j        S r?   )r  r  r3  s    r-   r   z8TableGroup.check_referential_integrity.<locals>.<lambda>v  s    8Q r,   r   c                     | j         S r?   )r  r3  s    r-   r   z8TableGroup.check_referential_integrity.<locals>.<lambda>z  s    QT r,   c                 D    g | ]}|j         t          |j                  fS r+   )r  rm   r  rj   r  s     r-   r   z:TableGroup.check_referential_integrity.<locals>.<listcomp>{  s'    !Q!Q!Qb2?E"%LL"A!Q!Q!Qr,   )rF   rG   rl  rU  r0  r   r"  rQ   r:  r   r  r1   	itertoolsgroupbyrl   r  r|   r}   rm   _check_fks_referencing_table)r;   rg  r  r  r%  r  r8  r  r)  rA   grpr  fksr  kgrpr  s                  @r-   check_referential_integrityz&TableGroup.check_referential_integrityV  s    M H I I I 	9[ 9 9-3 9 9B  9 9RRRRr?QRRRRR 9",!8#O#O#O#OB<N#O#O#O!8 !8#%#5!8 !8#9 #9 9999	?''))DGG 	? 	? 	?DGs1vv3g>>>>>>>>>	?  '.Q.QRR 	a 	aFAss))Cq6.L)++C%-c>>BB R RD!Q!QD!Q!Q!QE"II77sTZ\_``GGs   B 
C%(CCr  r  rH  r  c                     t          |t          j        d |D                       |          }|                    | |          } |                                D ]%\  }}|D ]\  }}|                    | |||          } &| S )z2Check all foreign keys referencing the same table.c              3   @   K   | ]}|t          |          d k    fV  dS )r   Nry   rC  s     r-   rk   z:TableGroup._check_fks_referencing_table.<locals>.<genexpr>  s1      1S1S2s2ww!|2D1S1S1S1S1S1Sr,   )ReferencedTabler|   r}   get_pksrp   	check_fks)	r  r  rH  r  r  r  source_tablesr  r  s	            r-   rF  z'TableGroup._check_fks_referencing_table  s     '+11S1Ss1S1S1SSSUXZ Z &&w77!$ 	P 	PB$1 P P b&00"lBOOPr,   )FFrN  )NNF)&r(   r)   r*   r0   r  r  rl   rl  r   r2   r   rd   r!  r   r   r1   rO   rP   r   r   r   rm   ro   r  r,  r   r&  r  r:  rJ  staticmethodr|   r}   r  r  r  rF  rC   rD   s   @r-   r   r     s          ,++DAAAFDKAAA
! 
! 
! 
! 
! 2 2 [2S S S (-(- 3,-tn  ~  dE4&7 89	   ""w|S01 " " " " 64U
+ 6 6 6 X6 d t<N7O    ,' ' ' 'R  (T%z@Q:R5S)ST 	
  
   \    r,   r   c            
           e Zd ZU dZeed<   ej        ee	f         ed<   e
j        ed<    ej        d           Zeeef         ed<   de	d	e	d
e	fdZde	ddded
e	fdZde	dededed
e	f
dZdS )rM  zN
    Wraps a Table object to simplify checking of foreign key references.
    rp  pksr  c                  4    t          j        t                    S r?   )r|   defaultdictr   r+   r,   r-   r   zReferencedTable.<lambda>  s     7 < < r,   r   refsr  r  r   c                 
   d | j         D             }| j                            | j                  D ]P}| j         D ]F} ||         |          }|| j        |         v r|rd}| j        |                             |           GQ|S )z'Read the actual fk values in the table.c                 ,    i | ]}|t          j        | S r+   )r  r  )rj   r  s     r-   rK  z+ReferencedTable.get_pks.<locals>.<dictcomp>  s"    GGGr8.3GGGr,   r  F)rS  rp  r  r  rV  r   )r;   r  r  itemgettersr  r  valss          r-   rN  zReferencedTable.get_pks  s    GGdhGGG:''DH'55 	( 	(Ch ( (&{2s++49R=((  ("'	"!!$''''( r,   rZ  	RefValuesr  c                 &   | j         |         }| j        |         }|j        |S |r"t          |j        t                    r|j        }n|j        g}|D ]>}|sd|v r	||vr1t          j        | d| j        j        j	         | j
                   d}?|S )zb
        We check if the value for the foreign key are available in the referenced table.
        Nz not found in table r  F)rV  rS  r   r7   rl   r   r  rp  rW  rM   r  )r;   r  rZ  r  rS  single_columnrV  refs           r-   _check_itemzReferencedTable._check_item  s     im;N 	!ZT:: 	! ;DDK=D 	  	 C  TS[[ #~~"HH1FHHdhX X X Xr,   r  r  c           	          |                     | j        d          D ]D\  }}}t          || t          j        | |                    }|                     |||          }E|S )z
        Check one fk constraint, i.e. whether the fk values in self.table actually can be found
        in `target_table`.
        Tr  rd  r  r   )r  r  r[  r  r  r_  )r;   r  r  r  r  rd  r  r  s           r-   rO  zReferencedTable.check_fks  sw     $0#9#9dhVZ#9#[#[ 	: 	:E645@X@SUW@XY]@^@^___D&&wb99GGr,   N)r(   r)   r*   r0   r   r2   r|   r}   r  r   r  r  r  r  rV  ro   r   rN  r_  rO  r+   r,   r-   rM  rM    s*          LLL 
	 T!1	2222	"3+"3<<#> #> #>D$z3
 > > >t T d    4 { 
 t    4   	
  
     r,   rM  c                   T    e Zd ZU dZeed<   eed<   eeee         f         ed<   d Z	dS )r[  z6Bundle properties of a table row for simpler checking.rd  r  r   c                 6    | j          d| j         d| j         dS )Nr  z Key ``ra  rX   s    r-   rY   zRefValues.__str__  s'    *@@t{@@$+@@@@r,   N)
r(   r)   r*   r0   r1   r2   r   r   rl   rY   r+   r,   r-   r[  r[    s[         @@JJJKKK#tCy.!!!!A A A A Ar,   r[  c            	           e Zd ZdZ	 	 	 ddedee         dedefd	Zd
 Ze	defd            Z
e	defd            Zeddeeef         fd            ZddZd Zd Zd ZdS )r$   zH
    Python API to read CSVW described data and convert it to JSON.
    NFTrW  md_urlr   r  c                    g | _         || _        d }t          j                    5 }|r(|                    t          j        d                    }d}	 t          j        |p|          }n2# t          j	        j
        $ r |                     |          \  }}Y nw xY wt          |                                          ddhk    | _        d|                    dd          vrt!          d          |                     |||           t%          | j        t(                    r| j        j        n| j        g| _        | j        D ]S}	|	j        j        D ]D}
|
j        r;t3          j        d	|
j                  s|
j                            d
          rd |
_        ET| j        j        | _        d d d            n# 1 swxY w Y   |r| j                             |           d S d S )NTrecordF@contextrW  http://www.w3.org/ns/csvwr   zInvalid or no @contextrA  rA   )rF   _strictr  r  r  catch_warningsr   r_  rG  decoderJSONDecodeErrorlocate_metadatar   r(  no_metadatar   rQ   _set_tablesr7   r%  r   rl  rU  r/  r   rC  rD  rB  common_propsextend)r;   rW  rf  r   r  rr  r  	no_headermdrp  r<  s              r-   rR   zCSVW.__init__  s/    !## 	4u N''(?t(L(L(LMMI:^FMc22 </ : : : $ 4 4S 9 9III:  #27799~~*e1DDD*"&&R2H2HHH !9:::Ri000+5dfj+I+IW$&--PTPVxDK ( ( ,4 ( (Cx (RYuch%?%? (38CVCVWZC[C[ (#'( !% 3D-	4 	4 	4 	4 	4 	4 	4 	4 	4 	4 	4 	4 	4 	4 	4.  	$M  #####	$ 	$s6   -F0A)(F0),BF0BDF00F47F4c                 r   d|v r|d         rt          |d         t                    st          d          t          |          r>t                              ||          | _        | j                            d           d S t                              ||          | _        d S t          |          r`t                              ||          | _        |r;| j        j
        rd| j        j
        _        d S t          d          | j        _
        d S d S t                              ||          | _        d S )Nrl  z-Invalid TableGroup with empty tables propertyrf  Tr  FrJ  )r7   rl   rQ   r#   r   rh  r%  r:  ri  r   rQ  r  r   )r;   rv  rW  ru  s       r-   rr  zCSVW._set_tables  s,   r>>h< Rz"X,'E'E R !PQQQc{{ <#,,Sr,::&&d&33333#--c-;;c{{ 7"55 ?v~ ?05---)0)>)>)>	? ? 266r,   r   c                    | j         rdS t          j        d          5 }| j        D ]C}|                    d          D ]}|                                st          j        d           D| j                            | j                  st          j        d           |r| j         	                    |           ddd           n# 1 swxY w Y   t          | j                    S )z
        Performs CSVW validation.

        .. note::

            For this to also catch problems during metadata location, the
            `CSVW` instance must be initialized with `validate=True`.
        FTrh  r  zDuplicate primary keyz"Referential integrity check failedN)rF   rm  rl  r  r  rG   
tablegrouprJ  rl  rt  r   )r;   rr  rp  rA   s       r-   is_validzCSVW.is_valid!  s2    = 	5$D111 		(Q ; ;66  A..00 ;M"9:::?>>dl>SS DBCCC ($$Q'''		( 		( 		( 		( 		( 		( 		( 		( 		( 		( 		( 		( 		( 		( 		( &&&&s   BCCCc                     t          | j        t                    r| j        n!t          d| j        j        i| j                  S )zThe table spec.rb   )r   rl  )r7   r%  r   rb   rl  rX   s    r-   ry  zCSVW.tablegroup9  s@     $DFJ77 Ktvv 5dkJJJ	Kr,   c                 x   d }d}| rt          |           rt          j        |           \  }}t          t	          j        d|                    }|D ]}|j                            d          dk    rg|j                            d          dv rKt          j        t          |j
                                      |                     } |||           r||fc S t          j        d           t          j        t          d	                              |                     }|j        d
k    r|j        nd}|                    d          D ]}	t          j        t          t%          |	                              |                                         |                     }|j        d
k    rQ	 |                                } |||           r||fc S t          j        d           # t(          j        $ r Y w xY wnp| rnt-          j        t1          |           dz                                             r8t          j        t-          j        t1          |           dz                       |fS d| d}t          | pd          s0t-          j        |           }
t1          |
          |d<   |
j        |d<   ||fS )u   
        Implements metadata discovery as specified in
        `§5. Locating Metadata <https://w3c.github.io/csvw/syntax/#locating-metadata>`_
        c                     |                      d| g          D ]C}|                    d          d         |d                             d          d         k    r dS DdS )Nrl  /rW  TF)r   r   )rv  rW  rp  s      r-   	describesz'CSVW.locate_metadata.<locals>.describesE  sf    2$//     99S>>"%u););C)@)@)DDD44 E5r,   Fzheader\s*=\s*absentreldescribedbyr   )zapplication/csvm+jsonzapplication/ld+jsonzapplication/jsonz?Ignoring linked metadata because it does not reference the dataz/.well-known/csvm   z&{+url}-metadata.json
csv-metadata.json
)rW  z8Ignoring metadata because it does not reference the dataz-metadata.jsonrk  )rj  rW  r   rk  rW  )r#   r   request_headr   rC  rD  paramsr   r_  r    rW  rc   rF   rG   rF  status_codetextr   r4   r  rG  ro  rO   rP   r1   r  r   )rW  r  ru  content_typelinkslinkrv  r   locslineps              r-   rp  zCSVW.locate_metadata?  s   	 	 	 	 $	\6#;; $	\ #("4S"9"9L%RY'=|LLMMI a a;??5))]::{v.. 3` ` `"^DNN,B,B3,G,GHH$9R-- 1#%y=000_````
 #D)<$=$=$E$Ec$J$JKKC"#55388;dD

4(( 	 	'[->->-E-E#-E-N-N(O(O(W(WX[(\(\]]?c)) XXZZ$9R-- 1#%y=000 &`aaaa/    *	  	\|CHH'7788??AA \~gl3s88>N3N&O&OPPR[[[3
 
 ciR   	  S!!Aq66CLCJI~s   0#G+G++G=<G=c                 f    t          j                    } j        j        rMt	           j        t
                    s3|                    t          j         j        j        d                      fd j	        D             |d<   |r+t          t          j        d |d         D                        S |S )zk
        Implements algorithm described in `<https://w3c.github.io/csvw/csv2json/#standard-mode>`_
        T)flatten_listc                 H    g | ]}|j         	                    |          S r+   )r  _table_to_json)rj   rp  r;   s     r-   r   z CSVW.to_json.<locals>.<listcomp>  sF     ] ] ]+0uG[]&&] ] ]r,   rl  c                 2    g | ]}d  |d         D             S )c                 *    g | ]}|d          d         S )r  r   r+   )rj   rs     r-   r   z+CSVW.to_json.<locals>.<listcomp>.<listcomp>  s!    "G"G"G1[>!#4"G"G"Gr,   r  r+   r/  s     r-   r   z CSVW.to_json.<locals>.<listcomp>  s+    !_!_!_A"G"Gah"G"G"G!_!_!_r,   )r|   r}   r%  rs  r7   r   updater   to_jsonrl  rl   rD  chain)r;   minimalr   s   `  r-   r  zCSVW.to_json  s     %'' 6 	Oz$&%'@'@ 	OJJv~df&9MMMNNN] ] ] ]48K] ] ]H 	b!_!_QTU]Q^!_!_!_`b b b 
r,   c                     t          j                    }t          j                            j                            |d<   dj        v rj        d         |d<   j        rt          j	        j                  |d<   |
                    t          j	        j                             t          j        d j        j        D                                                       D ]6}|                    d          |_        |                    d          |_        7 fdt%                              d	d
          d          D             }j        rd j        D             |d<   ||d<   |S )NrW  r   @idrR  c                      g | ]}|j         |fS r+   rJ  r  s     r-   r   z'CSVW._table_to_json.<locals>.<listcomp>  s    '_'_'_cS(9'_'_'_r,   r   r   c           	      P    g | ]"\  }\  }}}                     |||          #S r+   )_row_to_json)rj   rownumrA   rowsourcenumr  colsr;   rp  s        r-   r   z'CSVW._table_to_json.<locals>.<listcomp>  sJ     
 
 
..L# eT3EE
 
 
r,   TF)r  r  r   startc                     g | ]
}|d          S )r   r+   r6  s     r-   r   z'CSVW._table_to_json.<locals>.<listcomp>  s    "A"A"AA1Q4"A"A"Ar,   zrdfs:commentr  )r|   r}   r1   rW  rc   rb   r   rR  r   r  r  rs  rU  r/  r   r   r   r   r8  r  r
  )r;   rp  r   r<  r  r  s   ``   @r-   r  zCSVW._table_to_json  s   %''**5:6677E
5>!!-CJ; 	7!>%+66CL 	

6>%"455666&'_'_UEVE^'_'_'_``;;== 	3 	3C!kk-88CO;;z22CLL
 
 
 
 
 
2;d5AA3L 3L 3L
 
 

 ? 	B"A"A"A"A"ACE

r,   c                 r   t          j                    }|j                            |j                   d| |d<   ||d<   |j        j        rOd fd|j        j        D             D             |d<   t          |d                   dk    r|d         d         |d<   |                     |||          |d	<   |S )
Nz#row=rW  r  c                     g | ]}||S r+   r+   r/  s     r-   r   z%CSVW._row_to_json.<locals>.<listcomp>  s5     Y Y YVWYY Y Yr,   c                 :    g | ]}                     |          S r+   r   )rj   r   r  s     r-   r   z%CSVW._row_to_json.<locals>.<listcomp>  s#    RRRdCGGDMMRRRr,   rt   r   r   r  )	r|   r}   rW  rc   rb   rU  r2  rz   
_describes)r;   rp  r  r  r  r  r   s      `   r-   r  zCSVW._row_to_json  s    %''	))%*55JJLJJE
H& 	1Y YRRRRe6G6QRRRY Y YCM3x=!!Q&& #Ha 0H  ??5$VDDK
r,   c                 v   g }|j                             d          }|r@|                    t          j        d d|                    |||                               t          |                                d          D ]\  }\  }}	|                    |          }
|
r|
j	        s|
j
        r.|
r|
                                n|                                }t          |o|	|v |	dk    |	d u |
o|
j        o|	g k    g          r|                    t          j                            ||
||j         j        s| j        sd| n||	|                     |j         j        D ]E}
|
j
        r<|                    t          j                            ||
||
j        d |                     Ft          j        |          S )	Nr   r  )r  )aboutr   rf   r   r  r   r  )rU  r   rr   r   Tripler  r8  rp   r   r  r  r  r   r   from_colr/  rq  r  group_triples)r;   rp  r  r  r  triplesr   r;  rs   rJ   r<  r   s               r-   r  zCSVW._describes  s   $,,Z88 	]NN6=U%,,xSY,2Z2Z\ \ \ ] ] ] #399;;a888 	 	IAv1((1++C * ck  *-F3##%%%%2D2D2F2FDD&Q$YRdC<]CM<]VW[]V]^__ NN6=11$)$5$=^dFV^]^      $, 	b 	bC{ bv}55eS#szSWY_``aaa#G,,,r,   )NFTr?   rN  )r(   r)   r*   r0   r1   r   r   rR   rr  r   rz  r   ry  rQ  rm   ro   rp  r  r  r  r  r+   r,   r-   r$   r$     sF         %)""$ "$"$ SM"$ 	"$
 "$ "$ "$ "$H7 7 7( '$ ' ' ' X'. KJ K K K XK
 > >U4:%6 > > > \>@   "  6  - - - - -r,   r$   )Zr0   r  r  rC  rG  r+  r   rO   typingr   r   r   r   r   r  r   r  rF   r   rD  r  r|   collections.abcr   r	   r  urllib.parser
   r   r   language_tagsr   uritemplater   r   	datatypesr   dsvr   BaseDialectr   r   frictionlessr   r   metadata_utilsr   r   r   r   r   objectr  __all__r#   r   r   Decimaldate	timedeltar   rm   r1   r  r}   r  r%   r'   rH   	dataclassr4   rK   r    r!   r"   r   r   r  r   r.  rP  r  r  r  r   r  r   rM  r[  r$   r+   r,   r-   <module>r     sX    
			  				     9 9 9 9 9 9 9 9 9 9 9 9 9 9                     / / / / / / / /     6 6 6 6 6 6 6 6 6 6                             S S S S S S S S S S % % % % % %                    &((  
 
0A8CUUW3Z


!#s(
+GCLL	 	 	 	 	 	 	 	 '))     k   .
 
 
 
 
+) 
 
 
  )* )* )* )* )* )* )* )*X7) 7) 7) 7) 7)k- 7) 7) 7)t w, w, w, w, w, w, w, w,t E E E E E/ E E EP k k k k k[ k k k\ : : : : : : : :(        8 ^ ^ ^ ^ ^[ ^ ^ ^B _ _ _ _ _ _ _ _D d###       $# 
 
 
 
 
 
 
 
        * m) m) m) m) m)I m) m) m)`	 d###< < < < < < < $#<2 [ [ [ [ [ [ [ [| C C C C C C C CL d###A A A A A A A $#As- s- s- s- s- s- s- s- s- s-r,   