§
    ƒØjä7  ã                  óP  — U d dl mZ g 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m	Z	 d dlm
Z
  e
j        d¦  «        Z	 	 	 dd	„Z G d
„ d¦  «        Z G d„ d¦  «        Z G d„ dej        ¦  «        Z G d„ dej        ¦  «        Zg Zded<   edk    rd dlZ ej        e¦  «         dS dS )é    )Úannotations)ÚJobProcessorÚMetadataCachingJobÚcacheMetadataÚWorkerProcessN)Úcommon)Úenvironmentzmetadata.cachingTFc                óL  — ddl m} |                     d¬¦  «        }| €|dd…         ddgz   } t          j        | ¦  «        s| f} t          j        ¦   «         }|                     ¦   «          g }| D ]1}|                     |¦  «        }||                     |||¦  «        z  }Œ2d|› d	�}	|du rt           
                    |	¦  «         nt                               |	¦  «         |D ]@}
d
|
› �}	|du rt           
                    |	¦  «         Œ&t                               |	¦  «         ŒAdS )zv
    Cache metadata from corpora in `corpusNames` as local cache files.

    Call as ``metadata.cacheMetadata()``
    r   )ÚmanagerT)ÚskipNoneNÚlocalÚcorezcache: final writing time: z secondszpath failed to parse: )Úmusic21.corpusr   ÚlistLocalCorporaNamesr   Ú
isIterableÚTimerÚstartÚfromNamer   ÚenvironLocalÚwarnÚ
printDebug)ÚcorpusNamesÚuseMultiprocessingÚverboser   ÚlocalCorporaNamesÚtimerÚfailingFilePathsÚ
corpusNameÚcorpusObjectÚmessageÚfailingFilePaths              ú�/Users/tedpeters/Documents/Projects/Claude Projects/Misc Tools/notename-sheets/.venv/lib/python3.11/site-packages/music21/metadata/caching.pyr   r       sn  € ð 'Ð&Ð&Ð&Ð&Ð&à×5Ò5¸tÐ5ÑDÔDÐàÐØ'¨¨¨Ô*¨g°vÐ-@Ñ@ˆåÔ˜[Ñ)Ô)ð %Ø"�nˆåŒL‰NŒN€EØ	‡K‚K�M„M€Mð Ðð "ð [ð [ˆ
Ø×'Ò'¨
Ñ3Ô3ˆØ˜L×6Ò6Ð7IÈ7ÐTYÑZÔZÑZÐÐà;¨EÐ;Ð;Ð;€GØ�$€€Ý×Ò˜'Ñ"Ô"Ð"Ð"å×Ò Ñ(Ô(Ð(à+ð -ð -ˆØ<¨?Ð<Ð<ˆØ�dˆ?ˆ?Ý×Ò˜gÑ&Ô&Ð&Ð&å×#Ò# GÑ,Ô,Ð,Ð,ð-ð -ó    c                  óZ   — e Zd ZdZdd„Zd„ Zd„ Zd„ Zd	„ Zd
„ Z	d„ Z
d„ Zed„ ¦   «         ZdS )r   a
  
    Parses one corpus path, and attempts to extract metadata from it:

    >>> job = metadata.caching.MetadataCachingJob(
    ...     'bach/bwv66.6',
    ...     parseUsingCorpus=True,
    ...     corpusName='core',
    ...     )
    >>> job.jobNumber
    0
    >>> job.corpusName
    'core'
    >>> job.run()
    ((<music21.metadata.bundles.MetadataEntry 'bach_bwv66_6'>,), ())
    >>> results = job.getResults()
    >>> errors = job.getErrors()

    TODO: error list, not just numbers needs to be reported back up.
    r   TNc                ó²   — t          j        |¦  «        | _        g | _        t	          |¦  «        | _        g | _        t          |¦  «        | _        || _	        d S ©N)
ÚpathlibÚPathÚfilePathÚfilePathErrorsÚintÚ	jobNumberÚresultsÚboolÚparseUsingCorpusr   )Úselfr)   r,   r/   r   s        r"   Ú__init__zMetadataCachingJob.__init__e   sK   € Ýœ XÑ.Ô.ˆŒØ ˆÔÝ˜Y™œˆŒØˆŒÝ $Ð%5Ñ 6Ô 6ˆÔØ$ˆŒˆˆr#   c                óp  — dd l }g | _        |                      ¦   «         }t                               d| j        › d|› �¦  «         |�4d|j        v r|                      |¦  «         n|                      |¦  «         ~| 	                    ¦   «          |  
                    ¦   «         |                      ¦   «         fS )Nr   zGot ParsedObject from z: ÚOpus)Úgcr-   ÚparseFilePathr   r   r)   ÚclassesÚ	parseOpusÚparseNonOpusÚcollectÚ
getResultsÚ	getErrors)r0   r4   ÚparsedObjects      r"   ÚrunzMetadataCachingJob.runm   s¿   € Øˆ	ˆ	ˆ	ØˆŒØ×)Ò)Ñ+Ô+ˆÝ×ÒØD T¤]ÐDÐD°lÐDÐDñ	Fô 	Fð 	FàÐ#Ø˜Ô-Ð-Ð-Ø—’˜|Ñ,Ô,Ð,Ð,à×!Ò! ,Ñ/Ô/Ð/ØØ
�
Š
‰ŒˆØ�ŠÑ Ô  $§.¢.Ñ"2Ô"2Ð2Ð2r#   c                óÐ  — ddl m} ddl m} d }	 | j        du r|                     | j        d¬¦  «        }n)|                     t          | j        ¦  «        d¬¦  «        }n†# t          $ ry}t           	                    d| j        › d|› �¦  «         t           	                    t          j        ¦   «         ¦  «         | j                             | j        ¦  «         Y d }~nd }~ww xY w|S )	Nr   )Ú	converter)ÚcorpusFT)ÚforceSourcezparse failed: z, )Úmusic21r?   r@   r/   Úparser)   ÚstrÚ	Exceptionr   r   Ú	tracebackÚ
format_excr*   Úappend)r0   r?   r@   r<   Úes        r"   r5   z MetadataCachingJob.parseFilePath|   s
  € Ø%Ð%Ð%Ð%Ð%Ð%Ø"Ð"Ð"Ð"Ð"Ð"Øˆð	6ØÔ$¨Ð-Ð-Ø(Ÿš¨t¬}È$˜ÑOÔO��à%Ÿ|š|­C°´Ñ,>Ô,>ÈD˜|ÑQÔQ�øøÝð 	6ð 	6ð 	6Ý×#Ò#Ð$I°T´]Ð$IÐ$IÀaÐ$IÐ$IÑJÔJÐJÝ×#Ò#¥IÔ$8Ñ$:Ô$:Ñ;Ô;Ð;ØÔ×&Ò& t¤}Ñ5Ô5Ð5Ð5Ð5Ð5Ð5Ð5øøøøð	6øøøð Ðs   �AA  Á 
C#Á*A/CÃC#c                ór  — ddl m} 	 |j        j                             | j        ¦  «        }|j        �£|                     ¦   «         }|                     |j        ¦  «         |                     |¦  «         t           
                    d|› �¦  «         |j                             | j        || j        ¬¦  «        }| j                             |¦  «         d S t           
                    dt          j        t#          | j        ¦  «        ¦  «        › �¦  «         |j                             | j        d | j        ¬¦  «        }| j                             |¦  «         d S # t$          $ rR t                               d| j        › d�¦  «         t                               t+          j        ¦   «         ¦  «         Y d S w xY w)Nr   ©ÚmetadatazupdateMetadataCache: storing: )Ú
sourcePathÚmetadataPayloadr   z:addFromPaths: got stream without metadata, creating stub: z+Had a problem with extracting metadata for z, piece ignored)rB   rL   ÚbundlesÚMetadataBundleÚcorpusPathToKeyÚcleanFilePathÚRichMetadataÚmergeÚupdater   r   ÚMetadataEntryr   r-   rH   r   ÚrelativepathrD   rE   r   r)   rF   rG   )r0   r<   rL   Ú
corpusPathÚrichMetadataÚmetadataEntrys         r"   r8   zMetadataCachingJob.parseNonOpusŒ   sð  € Ø$Ð$Ð$Ð$Ð$Ð$ð	6Ø!Ô)Ô8×HÒHØÔ"ñ$ô $ˆJàÔ$Ð0Ø'×4Ò4Ñ6Ô6�Ø×"Ò" <Ô#8Ñ9Ô9Ð9Ø×#Ò# LÑ1Ô1Ð1Ý×'Ò'ØA°ZÐAÐAñCô Cð Cà (Ô 0× >Ò >Ø#Ô1Ø$0Ø#œð !?ñ !ô !�ð
 ”×#Ò# MÑ2Ô2Ð2Ð2Ð2å×'Ò'ðUÝ&,Ô&9½#¸dÔ>PÑ:QÔ:QÑ&RÔ&RðUð Uñô ð ð !)Ô 0× >Ò >Ø#Ô1Ø$(Ø#œð !?ñ !ô !�ð
 ”×#Ò# MÑ2Ô2Ð2Ð2Ð2øÝð 	6ð 	6ð 	6Ý×Òð6Ø”}ð6ð 6ð 6ñô ð õ ×Ò�iÔ2Ñ4Ô4Ñ5Ô5Ð5Ð5Ð5Ð5ð	6øøøs   ˆCE ÃBE ÅAF6Æ5F6c           	     óÆ  — ddl m} d}	 t          |j        ¦  «        D ]\  }}|                      ||¦  «         ~Œnj# t
          $ r]}t                               d|› d| j        › d|› �¦  «         t           	                    t          j        ¦   «         ¦  «         Y d }~nd }~ww xY w|j                             | j        d ¬¦  «        }| j                             |¦  «         d S )Nr   rK   ú1Had a problem with extracting metadata for score ú in ú, whole opus ignored: )rM   rN   )rB   rL   Ú	enumerateÚscoresÚparseScoreInsideOpusrE   r   r   r)   r   rF   rG   rO   rV   rR   r-   rH   )r0   r<   rL   ÚscoreNumberÚscoreÚ	exceptionrZ   s          r"   r7   zMetadataCachingJob.parseOpus¯   s:  € Ø$Ð$Ð$Ð$Ð$Ð$ð ˆð
	<Ý&/°Ô0CÑ&DÔ&Dð ð Ñ"�˜UØ×)Ò)¨%°Ñ=Ô=Ð=Ø�Eðøõ ð 	<ð 	<ð 	<Ý×ÒðØðð Ø$(¤Mðð àðð ñô ð õ
 ×#Ò#¥IÔ$8Ñ$:Ô$:Ñ;Ô;Ð;Ð;Ð;Ð;Ð;Ð;øøøøð	<øøøð !Ô(×6Ò6ØÔ)Ø ð 7ñ 
ô 
ˆð 	Œ×Ò˜MÑ*Ô*Ð*Ð*Ð*s   Š1< ¼
B#ÁABÂB#c           	     ó  — ddl m} 	 |                     ¦   «         }|                     |j        ¦  «         |                     |¦  «         |j        �|j        j        €1t                               dt          | j	        ¦  «        z   ¦  «         d S |j
        j                             | j        |j        j        ¬¦  «        }t                               d|› �¦  «         |j
                             | j        |j        j        |¬¦  «        }| j                             |¦  «         d S # t"          $ r^}t                               d|› d| j	        › d	|› �¦  «         t                               t'          j        ¦   «         ¦  «         Y d }~d S d }~ww xY w)
Nr   rK   zLaddFromPaths: got Opus that contains Streams that do not have work numbers: )ÚnumberzaddFromPaths: storing: )rM   rf   rN   r\   r]   r^   )rB   rL   rS   rT   rU   rf   r   r   rD   r)   rO   rP   rQ   rR   rV   r-   rH   rE   r   rF   rG   )r0   rc   rb   rL   rY   rX   rZ   rd   s           r"   ra   z'MetadataCachingJob.parseScoreInsideOpusÉ   sà  € ð 	%Ð$Ð$Ð$Ð$Ð$ð	<à#×0Ò0Ñ2Ô2ˆLØ×Ò˜uœ~Ñ.Ô.Ð.Ø×Ò Ñ&Ô&Ð&ØŒ~Ð%¨¬Ô)>Ð)FÝ×'Ò'ð@å˜$œ-Ñ(Ô(ñ)ñô ð ð ð ð &Ô-Ô<×LÒLØÔ&Ø œ>Ô0ð Mñ ô �
õ ×'Ò'Ø:¨jÐ:Ð:ñ<ô <ð <à (Ô 0× >Ò >Ø#Ô1Ø œ>Ô0Ø$0ð !?ñ !ô !�ð
 ”×#Ò# MÑ2Ô2Ð2Ð2Ð2øÝð 	<ð 	<ð 	<Ý×ÒðGÀKð Gð GØ”mðGð GØ;DðGð Gñô ð õ ×#Ò#¥IÔ$8Ñ$:Ô$:Ñ;Ô;Ð;Ð;Ð;Ð;Ð;Ð;Ð;øøøøð	<øøøs    ˆBD$ ÂBD$ Ä$
FÄ.AFÆFc                ó*   — t          | j        ¦  «        S r&   )Útupler*   ©r0   s    r"   r;   zMetadataCachingJob.getErrorsð   s   € Ý�TÔ(Ñ)Ô)Ð)r#   c                ó*   — t          | j        ¦  «        S r&   )rh   r-   ri   s    r"   r:   zMetadataCachingJob.getResultsó   s   € Ý�T”\Ñ"Ô"Ð"r#   c                ó’   — t          j        ¦   «         }	 | j                             |¦  «        }n# t          $ r
 | j        }Y nw xY w|S r&   )r   ÚgetCorpusFilePathr)   Úrelative_toÚ
ValueError)r0   rX   rR   s      r"   rR   z MetadataCachingJob.cleanFilePathø   sX   € åÔ-Ñ/Ô/ˆ
ð	*Ø œM×5Ò5°jÑAÔAˆMˆMøÝð 	*ð 	*ð 	*Ø œMˆMˆMˆMð	*øøøàÐs   •0 °AÁA)r   TN)Ú__name__Ú
__module__Ú__qualname__Ú__doc__r1   r=   r5   r8   r7   ra   r;   r:   ÚpropertyrR   © r#   r"   r   r   O   s¸   € € € € € ðð ð*%ð %ð %ð %ð3ð 3ð 3ðð ð ð !6ð !6ð !6ðF+ð +ð +ð4#<ð #<ð #<ðN*ð *ð *ð#ð #ð #ð
 ðð ñ „Xðð ð r#   r   c                  óX   — e Zd ZdZed„ ¦   «         Zedd„¦   «         Zed	d„¦   «         ZdS )
r   a2  
    Processes metadata-caching jobs, either serially (e.g. single-threaded) or
    in parallel, as a generator.

    Yields a dictionary of:

    * MetadataEntry instances
    * failed file paths
    * the last processed file path
    * the number of remaining jobs

    >>> jobs = []
    >>> mdb = corpus.corpora.CoreCorpus().search('monteverdi')[:3]
    >>> paths = [x.sourcePath for x in mdb]

    >>> for corpusPath in paths:
    ...     job = metadata.caching.MetadataCachingJob(
    ...         corpusPath,
    ...         parseUsingCorpus=True,
    ...         corpusName='core',
    ...         )
    ...     jobs.append(job)
    >>> jobGenerator = metadata.caching.JobProcessor.process_serial(jobs)
    >>> for result in jobGenerator:
    ...     print(result['remainingJobs'])
    ...
    2
    1
    0
    c                ó,   — | |z
  }d|› d| › d|› d|› �}|S )z3
        Report on the current job status.
        zupdated z of z files; total errors: z ... last file: rt   )Ú	totalJobsÚremainingJobsr)   ÚfilePathErrorCountÚcompletedJobsr    s         r"   Ú_reportzJobProcessor._report'  sQ   € ð
 " MÑ1ˆð%�}ð %ð %¨)ð %ð %Ø/ð%ð %à"ð%ð %ð 	ð
 ˆr#   Nc              #  óÌ  ‡
‡K  — |pt          j        ¦   «         }t          |d¦  «        }t          | ¦  «        }t	          ||¦  «        }t
                               d|› d|› d�¦  «         g }t          j        ¦   «         Š
t          j	        ¦   «         Šˆ
ˆfd„t          |¦  «        D ¦   «         }|D ]}|                     ¦   «          Œ| r¬| D ])}‰
                     t          j        |¦  «        ¦  «         Œ*t          t          | ¦  «        ¦  «        D ]c}t          j        ‰                     ¦   «         ¦  «        }|                     ¦   «         }|                     ¦   «         }|dz  }|||j        |dœV — Œd|D ]}	‰
                     d¦  «         Œ‰
                     ¦   «          ‰                     ¦   «          ‰
                     ¦   «          |D ]}|                     ¦   «          ŒdS )a  
        Process jobs in parallel, with `processCount` processes.

        If `processCount` is none, use 1 fewer process than the number of
        available cores.

        jobs is a list of :class:`~music21.metadata.MetadataCachingJob` objects.

        é   zProcessing z jobs in parallel, with z processes.c                ó0   •— g | ]}t          ‰‰¦  «        ‘ŒS rt   )r   )Ú.0Ú_Ú	job_queueÚresult_queues     €€r"   ú
<listcomp>z1JobProcessor.process_parallel.<locals>.<listcomp>L  s3   ø€ ð 1ð 1ð 1Øõ ! ¨LÑ9Ô9ð 1ð 1ð 1r#   ©ÚmetadataEntriesÚerrorsr)   rx   N)r   ÚcpusÚmaxÚlenÚminr   r   ÚmultiprocessingÚJoinableQueueÚQueueÚranger   ÚputÚpickleÚdumpsÚloadsÚgetr:   r;   r)   ÚjoinÚclose)ÚjobsÚprocessCountrx   r-   ÚworkersÚworkerÚjobÚunused_jobCounterr†   Ú_workerr�   r‚   s             @@r"   Úprocess_parallelzJobProcessor.process_parallel6  s)  øøè è € ð $Ð4¥v¤{¡}¤}ˆÝ˜<¨Ñ+Ô+ˆå˜D™	œ	ˆÝ˜<¨Ñ7Ô7ˆå×ÒØZ˜-ÐZÐZÀÐZÐZÐZñ	\ô 	\ð 	\àˆÝ#Ô1Ñ3Ô3ˆ	Ý&Ô,Ñ.Ô.ˆð1ð 1ð 1ð 1ð 1Ý! ,Ñ/Ô/ð1ñ 1ô 1ˆàð 	ð 	ˆFØ�LŠL‰NŒNˆNˆNØð 	Øð 1ð 1�Ø—’�fœl¨3Ñ/Ô/Ñ0Ô0Ð0Ð0Ý%*­3¨t©9¬9Ñ%5Ô%5ð 
ð 
Ð!Ý”l <×#3Ò#3Ñ#5Ô#5Ñ6Ô6�ØŸ.š.Ñ*Ô*�ØŸš™œ�Ø Ñ"�à'.Ø$Ø #¤Ø%2ð	ð ð ð ð ð ð ð 	 ð 	 ˆGØ�MŠM˜$ÑÔÐÐØ�ŠÑÔÐØ×ÒÑÔÐØ�ŠÑÔÐØð 	ð 	ˆFØ�KŠK‰MŒMˆMˆMð	ð 	r#   r–   úlist[MetadataCachingJob]c              #  ó†   K  — t          | ¦  «        }| D ],}|                     ¦   «         \  }}|dz  }|||j        |dœV — Œ-dS )z(
        Process jobs serially.
        r}   r„   N)r‰   r=   r)   )r–   rx   rš   r-   r†   s        r"   Úprocess_serialzJobProcessor.process_serialg  ss   è è € õ
 ˜D™	œ	ˆØð 	ð 	ˆCØ!Ÿgšg™iœi‰OˆG�VØ˜QÑˆMà#*Ø ØœLØ!.ð	ð ð ð ð ð ð	ð 	r#   r&   )r–   rž   )ro   rp   rq   rr   Ústaticmethodr{   r�   r    rt   r#   r"   r   r     s{   € € € € € ðð ðB ð
ð 
ñ „\ð
ð ð-ð -ð -ñ „\ð-ð` ðð ð ñ „\ðð ð r#   r   c                  ó(   ‡ — e Zd ZdZˆ fd„Zd„ Zˆ xZS )r   z[
    A worker process for use by the multithreaded metadata-caching job
    processor.
    c                ód   •— t          ¦   «                              ¦   «          || _        || _        d S r&   )Úsuperr1   r�   r‚   )r0   r�   r‚   Ú	__class__s      €r"   r1   zWorkerProcess.__init__„  s.   ø€ Ý‰Œ×ÒÑÔÐØ"ˆŒØ(ˆÔÐÐr#   c                óP  — 	 | j                              ¦   «         }|€| j                              ¦   «          d S t          j        |¦  «        }|                     ¦   «          | j                              ¦   «          | j                             t          j        |d¬¦  «        ¦  «         Œ¦)NTr   )Úprotocol)	r�   r“   Ú	task_doner�   r’   r=   r‚   r�   r‘   )r0   rš   s     r"   r=   zWorkerProcess.run‹  s•   € ð		AØ”.×$Ò$Ñ&Ô&ˆCàˆ{Ø”×(Ò(Ñ*Ô*Ð*Ø�Ý”,˜sÑ#Ô#ˆCØ�GŠG‰IŒIˆIØŒN×$Ò$Ñ&Ô&Ð&ØÔ×!Ò!¥&¤,¨s¸QÐ"?Ñ"?Ô"?Ñ@Ô@Ð@ð		Ar#   )ro   rp   rq   rr   r1   r=   Ú__classcell__)r¥   s   @r"   r   r   |  sX   ø€ € € € € ðð ð)ð )ð )ð )ð )ð
Að 
Að 
Að 
Að 
Að 
Að 
Ar#   r   c                  ó   — e Zd ZdS )ÚTestN)ro   rp   rq   rt   r#   r"   r«   r«   ›  s   € € € € € Ø€Dr#   r«   z
list[type]Ú
_DOC_ORDERÚ__main__)NTF)Ú
__future__r   Ú__all__r‹   r'   r�   rF   ÚunittestrB   r   r	   ÚEnvironmentr   r   r   r   ÚProcessr   ÚTestCaser«   r¬   Ú__annotations__ro   ÚmainTestrt   r#   r"   ú<module>r¶      sÅ  ðð #Ð "Ð "Ð "Ð "Ð "Ð "ðð ð €ð Ð Ð Ð Ø €€€Ø €€€Ø Ð Ð Ð Ø €€€à Ð Ð Ð Ð Ð Ø Ð Ð Ð Ð Ð à&ˆ{Ô&Ð'9Ñ:Ô:€ð #Ø%)Øð)-ð )-ð )-ð )-ð^pð pð pð pð pñ pô pð pðlpð pð pð pð pñ pô pð pðnAð Að Að Að A�OÔ+ñ Aô Að Að>	ð 	ð 	ð 	ð 	ˆ8Ôñ 	ô 	ð 	ð
 €
Ð Ð Ð Ñ àˆzÒÐØ€N€N€NØ€GÔ�TÑÔÐÐÐð Ðr#   