o
    i{                     @   s@  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Zddl	m
Z
 ddlmZ ddlmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZm Z m!Z! ddd	d
d
ddddddddZ"dddddddddZ#dd Z$dd Z%G dd  d eZ&G d!d" d"e
Z'G d#d$ d$e'Z(G d%d& d&e'Z)G d'd( d(e)Z*G d)d* d*e'Z+G d+d, d,e'Z,G d-d. d.e'Z-G d/d0 d0e'Z.G d1d2 d2e.Z/G d3d4 d4e.Z0G d5d6 d6e.Z1G d7d8 d8e.Z2G d9d: d:e.Z3G d;d< d<e3Z4G d=d> d>e3Z5G d?d@ d@e'Z6G dAdB dBe'Z7G dCdD dDe'Z8G dEdF dFe'Z9dS )G    N   )PostProcessor   )imghdr)MEDIA_EXTENSIONSISO639UtilsPopenPostProcessingError_get_exe_version_outputdeprecation_warningdetect_exe_versiondetermine_extdfxp2srtencodeArgumentfilter_dictfloat_or_noneis_outdated_version
orderedSetprepend_extensionreplace_extensionshell_quotetraverse_objvariadicwrite_json_fileadtsflacipodmatroskampegoggmpegtsasfwebmwebvtt)aacr   m4amkamkvmpgogvtswmawmvwebavtt)mp3
libmp3lame )r%   r$   )-fr   )r%   r$   )-bsf:aaac_adtstoasc)opuslibopusr1   )r   	libvorbisr1   )r   r   r1   )r%   N)-acodecalac)wavN)r2   r:   )r/   r$   r%   r5   vorbisr   r9   r:   c              	   C   s   t ddd| S )Nz{0}(?:/{0})*$z(?:\s*\w+\s*>)?\s*(?:{})\s*|)recompileformatjoin)	supportedr1   r1   O/home/ubuntu/.local/lib/python3.10/site-packages/yt_dlp/postprocessor/ffmpeg.pycreate_mapping_re?   s   rC   c                 C   s|   |  dD ]/}|dd}t|dks|d  | kr6|d  }|| kr0|d|  f  S |df  S qdd|  fS )	zo
    Get corresponding item from a mapping string like 'A>B/C>D/E'
    @returns    (target, error_message)
    />r   r   zalready is in target format Nzcould not find a mapping for )lowersplitlenstrip)sourcemappingpairkvtargetr1   r1   rB   resolve_mappingC   s   rP   c                   @   s   e Zd ZdS )FFmpegPostProcessorErrorN)__name__
__module____qualname__r1   r1   r1   rB   rQ   R   s    rQ   c                   @   s  e Zd ZejdddZdGddZedGddZedGdd	Z	d
d Z
ddii ZZdd Zedd Zejdd Zejdd Zdd Zejdd Zejdd Zedd Zedd Zedd Zed d! ZedHdd#d$d%Zd&d' Zd(d) Zg fd*d+Zd,d- Zd.d/ Z dHd0d1Z!dId3d4Z"d5d6 Z#d7d8d9d:Z$d;d< Z%ed=d> Z&ed?d@ Z'dAdB Z(dGdCdDZ)e*dGdEdFZ+dS )JFFmpegPostProcessorffmpeg_locationN)defaultc                 C   s   t | | |  | _d S N)r   __init___determine_executables_paths)self
downloaderr1   r1   rB   rY   Y   s   zFFmpegPostProcessor.__init__c                 C   s   t | }|j|jfS rX   )rU   	_versions	_features)r]   ppr1   r1   rB   get_versions_and_features]   s   z-FFmpegPostProcessor.get_versions_and_featuresc                 C   s   t | d S )Nr   )rU   ra   )r]   r1   r1   rB   get_versionsb      z FFmpegPostProcessor.get_versionsc                    s  ddg}|  d| j }|d u rdd |D S tj|s+| jd| ddd	 i S tj|r:|d d  }ntj|t	fd
d|D d}tj
tj|  fdd|D }|r|v r|D ]}tj ||}tj|r~|||< qg|r|||< |S )NffmpegffproberV   c                 S   s   i | ]}||qS r1   r1   .0pr1   r1   rB   
<dictcomp>k   s    z>FFmpegPostProcessor._determine_executables.<locals>.<dictcomp>zffmpeg-location z* does not exist! Continuing without ffmpegT)	only_oncec                 3   s    | ]	}| v r|V  qd S rX   r1   rf   )filenamer1   rB   	<genexpr>u   s    z=FFmpegPostProcessor._determine_executables.<locals>.<genexpr>c                    s   i | ]
}|t j |qS r1   )ospathr@   rf   )dirnamer1   rB   ri   x   s    )	get_param_ffmpeg_locationgetrm   rn   existsreport_warningisdirbasenamenextro   abspathr@   replace)r\   programslocationrv   pathsrh   rn   r1   )ro   rk   rB   rZ   f   s0   z*FFmpegPostProcessor._determine_executablesc           
      C   s   | j |}|| jv r| j| | j|i fS t|dg}|r#t|nd}|r=ddg}|D ]}t||}|r<|d}q-|| j|< |dksH|sL|i fS t	d|}|r]|d
d	d
nd }d|v d| v t|ddd | j|< }	||	fS )Nz-bsfsFz'(?:\d+:)?([0-9.]+)-[0-9]+ubuntu[0-9.]+$zn([0-9.]+)$r   rd   z>(?m)^\s+libavformat\s+(?:[0-9. ]+)\s+/\s+(?P<runtime>[0-9. ]+)runtime  z--enable-libfdk-aacsettsz	57.56.100)fdkr   needs_adtstoasc)r[   rr   _version_cache_features_cacher
   r   r=   matchgroupsearchry   
splitlinesr   )
r\   progrn   outverregexsregexmobjlavf_runtime_versionfeaturesr1   r1   rB   _get_ffmpeg_version   s0   




z'FFmpegPostProcessor._get_ffmpeg_versionc                 C   s   t | j| j| j| jiS rX   )r   rv   _versionprobe_basename_probe_versionr\   r1   r1   rB   r^      s   zFFmpegPostProcessor._versionsc                 C      | j }| jS rX   )r   rv   r\   _r1   r1   rB   rv         zFFmpegPostProcessor.basenamec                 C   r   rX   )r   r   r   r1   r1   rB   r      r   z"FFmpegPostProcessor.probe_basenamec                    sX   |f}t tdd  fdd|D d d i f\}}}|dkr'|| _ _|S | _|S )Nc                 S   s   | d S Nr   r1   )xr1   r1   rB   <lambda>   s    z2FFmpegPostProcessor._get_version.<locals>.<lambda>c                 3   s"    | ]}|g  |R V  qd S rX   )r   rf   r   r1   rB   rl      s     z3FFmpegPostProcessor._get_version.<locals>.<genexpr>rd   )rw   filterrv   r_   r   )r\   kindexecutablesrv   versionr   r1   r   rB   _get_version   s   
z FFmpegPostProcessor._get_versionc                 C   
   |  dS )Nrd   r   r   r1   r1   rB   r         
zFFmpegPostProcessor._versionc                 C   r   )Nre   r   r   r1   r1   rB   r      r   z"FFmpegPostProcessor._probe_versionc                 C   
   | j d uS rX   )rv   r   r1   r1   rB   	available   s   
zFFmpegPostProcessor.availablec                 C      | j | jS rX   )r[   rr   rv   r   r1   r1   rB   
executable   rc   zFFmpegPostProcessor.executablec                 C   r   rX   )r   r   r1   r1   rB   probe_available   r   z#FFmpegPostProcessor.probe_availablec                 C   r   rX   )r[   rr   r   r   r1   r1   rB   probe_executable   rc   z$FFmpegPostProcessor.probe_executableTextc                c   s>    dE d H  dE d H  | rdE d H  |dv rdE d H  d S d S )N)-map0)z-dnz-ignore_unknown)-ccopy)mp4movr%   )z-c:smov_textr1   )r   r   r1   r1   rB   stream_copy_opts   s   


z$FFmpegPostProcessor.stream_copy_optsc              	   C   sH   | j stdd}t| j|r"| d| j d| j d| d d S d S )NzLffmpeg not found. Please install or provide the path using --ffmpeg-locationz1.0zYour copy of z is outdated, update z to version z% or newer if you encounter any errors)r   rQ   r   r   rt   rv   )r\   required_versionr1   r1   rB   check_version   s   z!FFmpegPostProcessor.check_versionc           
      C   s8  | j s
| js
tdzE| j r| jtdg}n| jtdg}|| | | | j	 dt
|  tj|dtjtjtjd\}}}|| j rHdndkrNW d S W n
 tyY   Y d S w | j r_|n|}| j rd }|d	D ]}|d
r||dd  }qk| dkr|d ur|  S qkd S td|}	|	r|	dS d S )NzXffprobe and ffmpeg not found. Please install or provide the path using --ffmpeg-location-show_streams-iz command line: T)textstdinstdoutstderrr   r   
zcodec_name==zcodec_type=audiozNStream\s*#\d+:\d+(?:\[0x[0-9a-f]+\])?(?:\([a-z]{3}\))?:\s*Audio:\s*([0-9a-z]+))r   r   r	   r   r   r   append_ffmpeg_filename_argumentwrite_debugrv   r   r   run
subprocessPIPEOSErrorrH   
startswithrJ   r=   r   r   )
r\   rn   cmdr   r   
returncodeoutputaudio_codecliner   r1   r1   rB   get_audio_codec   sL   

z#FFmpegPostProcessor.get_audio_codecc                 C   s   | j dkr| jr| d td|   | jtdtdtdtdtdg}||7 }|| | | 	d	t
|  tj|d
tjtjtjd\}}}t|S )Nre   z1Only ffprobe is supported for metadata extractionzMffprobe not found. Please install or provide the path using --ffmpeg-location-hide_bannerz-show_formatr   z-print_formatjsonzffprobe command line: Tr   r   r   r   )r   r   rt   r	   r   r   r   r   r   r   r   r   r   r   r   r   loads)r\   rn   optsr   r   r   r1   r1   rB   get_metadata_object  s"   

	 
z'FFmpegPostProcessor.get_metadata_objectc                    s8   |  |d }t fddt|D d }|t|fS )Nstreamsc                 3   s*    | ]\}}t | d dkr|V  qdS )F	casesenseN)r   )rg   istreamkeysvaluer1   rB   rl   &  s   ( z8FFmpegPostProcessor.get_stream_number.<locals>.<genexpr>)r   rw   	enumeraterI   )r\   rn   r   r   r   numr1   r   rB   get_stream_number#  s   z%FFmpegPostProcessor.get_stream_numberc                 C   s6   t |d}|r|ds| |d |d< d S d S d S )N)chaptersrF   end_timefilepath)r   rr   _get_real_video_duration)r\   infolast_chapterr1   r1   rB   _fixup_chapters*  s   
z#FFmpegPostProcessor._fixup_chaptersc              
   C   sb   zt t| |d}|std|W S  ty0 } z|r%td|j W Y d }~d S d }~ww )N)r?   durationzffprobe returned empty durationz$Unable to determine video duration: )r   r   r   r	   msg)r\   r   fatalr   er1   r1   rB   r   /  s   z,FFmpegPostProcessor._get_real_video_durationr   c                 C   s   |r|sd S t || |kS rX   )abs)r\   d1d2	tolerancer1   r1   rB   _duration_mismatch:  s   z&FFmpegPostProcessor._duration_mismatchc                 K   s$   | j dd |D ||fgfi |S )Nc                 S   s   g | ]}|g fqS r1   r1   )rg   rn   r1   r1   rB   
<listcomp>C      zAFFmpegPostProcessor.run_ffmpeg_multiple_files.<locals>.<listcomp>)real_run_ffmpeg)r\   input_pathsout_pathr   kwargsr1   r1   rB   run_ffmpeg_multiple_filesA  s   z-FFmpegPostProcessor.run_ffmpeg_multiple_files)r   )expected_retcodesc                   s     tdd |D }jtdg}jdkr#|tdtdg7 }fddd	|fd
|ffD ]\ }|tj fddt|D 7 }q1	dt
|  tj|dtjtjtjd\}}}	|	t|vrw	| t|  d |D ]\}
}|
r|
|| qy|S )Nc                 s   s$    | ]\}}|rt |jV  qd S rX   )rm   statst_mtime)rg   rn   r   r1   r1   rB   rl   I  s    

z6FFmpegPostProcessor.real_run_ffmpeg.<locals>.<genexpr>z-yrd   z	-loglevelzrepeat+infoc                    s|   d| | d| g}|dkr|ddg7 }|dkr| d |  j|7 }|dkr1| d d	d
 |D  | g S )Nr   oz	-movflagsz
+faststartr   r   r   r   c                 S   s   g | ]}t |qS r1   )r   )rg   argr1   r1   rB   r   [  r   zJFFmpegPostProcessor.real_run_ffmpeg.<locals>.make_args.<locals>.<listcomp>)r   _configuration_argsrv   r   )fileargsnamenumberr   r   r1   rB   	make_argsQ  s   


z6FFmpegPostProcessor.real_run_ffmpeg.<locals>.make_argsr   r   c                 3   s2    | ]\}\}}|r|t | |d  V  qdS )r   N)list)rg   r   rn   r   )arg_typer   r1   rB   rl   _  s    
zffmpeg command line: Tr   rF   )r   minr   r   rv   	itertoolschainfrom_iterabler   r   r   r   r   r   r   r   rQ   rJ   r   	try_utime)r\   input_path_optsoutput_path_optsr   oldest_mtimer   	path_optsr   r   r   r   r1   )r  r   r\   rB   r   F  s0   

z#FFmpegPostProcessor.real_run_ffmpegc                 K   s   | j |g||fi |S rX   )r   )r\   rn   r   r   r   r1   r1   rB   
run_ffmpegn  s   zFFmpegPostProcessor.run_ffmpegc                 C   s"   |  dr| S | dkrd|  S | S )N)zhttp://zhttps://-zfile:)r   )fnr1   r1   rB   r   q  s   
z-FFmpegPostProcessor._ffmpeg_filename_argumentc                 C   sT   |  dd dd} | d dkr| dd  nd|  } | d dkr&| d d S | d S )N'z'\''z'''r   r   rF   )ry   )stringr1   r1   rB   _quote_for_ffmpeg{  s     z%FFmpegPostProcessor._quote_for_ffmpegc              	   C   sx   t |}|d dkr|dd  }t|d}| d| d | ||g | jdt|ddd	d
d |D  |S )Nr   r   zkeyframes.tempzRe-encoding "z" with appropriate keyframesFr   z-force_key_frames,c                 s   s    | ]}|d V  qdS )z.6fNr1   )rg   tr1   r1   rB   rl         z6FFmpegPostProcessor.force_keyframes.<locals>.<genexpr>)r   r   	to_screenr  r   r   r@   )r\   rk   
timestampskeyframe_filer1   r1   rB   force_keyframes  s   

z#FFmpegPostProcessor.force_keyframesc                 C   s   | d}|  d|  t|ddd}|| || W d   n1 s(w   Y  t| jt|d}| |g dfg||fg | | dS )	z
        Use concat demuxer to concatenate multiple files having identical streams.

        Only inpoint, outpoint, and duration concat options are supported.
        See https://ffmpeg.org/ffmpeg-formats.html#concat-1 for details
        z.concatzWriting concat spec to wutf-8encodingNr   )r   z-nostdinr2   concatz-safer   )	r   open
writelines_concat_specr   r   r   r   _delete_downloaded_files)r\   in_filesout_fileconcat_optsconcat_filef	out_flagsr1   r1   rB   concat_files  s   
z FFmpegPostProcessor.concat_filesc                 c   s|    |d u ri gt | }dV  t||ddD ]%\}}d| | | dV  dD ]}||v r:| d||  dV  q)qd S )Nzffconcat version 1.0
Tstrictzfile r   )inpointoutpointr   r~   )rI   zipr  r   )clsr!  r#  r   r   	directiver1   r1   rB   r    s   z FFmpegPostProcessor._concat_specrX   )T)r   ),rR   rS   rT   contextvars
ContextVarrq   rY   staticmethodra   rb   rZ   r   r   r   propertyr^   	functoolscached_propertyrv   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r  r   r  r  r'  classmethodr  r1   r1   r1   rB   rU   V   sb    











	%

(
	
	
rU   c                   @   sf   e Zd Zg ejdR Zee Z	e
dge	R ZdddZdd Zd	d
 Zejdddd ZdS )FFmpegExtractAudioPPr+   bestNFc                 C   s*   t | | |p	d| _t|| _|| _d S )Nr7  )rU   rY   rL   r   _preferredquality_nopostoverwrites)r\   r]   preferredcodecpreferredqualitynopostoverwritesr1   r1   rB   rY     s   


zFFmpegExtractAudioPP.__init__c                 C   s   | j d u rg S | j dkrd| j  dgS ddddd|}|s"g S |d	 |d
 |d	  | j d   }|dkr>dt| gS d| gS )N
   z-b:ak)r=  r   )r   r=  )g?   )r      )r0   r7   r$   
libfdk_aacr   r   rA  z-vbrz-q:a)r8  rr   int)r\   codeclimitsqr1   r1   rB   _quality_args  s"   

"
z"FFmpegExtractAudioPP._quality_argsc              
   C   sd   |d u rg }nd|g}dg||}zt | ||| W d S  ty1 } ztd|j d }~ww )Nr8   -vnzaudio conversion failed: )rU   r  rQ   r	   r   )r\   rn   r   rC  	more_optsacodec_optsr   errr1   r1   rB   r    s   zFFmpegExtractAudioPP.run_ffmpegimagesc                 C   sF  |d  }}t |d | j\}}|dkr|d | jv rd\}}|s0| d| d|  g |fS | |}|d u r=td|dkrS|d	v rSg td
 dR \}}}	}
n>|dks[||kr{zg t| dR \}}}	}
W n& tyz   td \}}
}	Y nw t| \}}
}	|
dkr| j	drdg }
}	t
|	}	|
dkr| |
}	t|||d  }}||kr|
dkr| d| d|  g |fS t|d}t|d}| jrtj|rtj|r| d| d g |fS | d|  | |||
|	 t|| t|| ||d< ||d< |	dd ur| j|t |d dd |g|fS )Nr   r   r7  )Nz,the file is already in a common audio formatzNot converting audio z; z7WARNING: unable to obtain file audio codec with ffprober$   )r%   r7  r%   r   r/   r   rA  z#; file is already in target format origtempzPost-process file z exists, skippingzDestination: filetimez!Cannot update utime of audio file)errnote)rP   rL   COMMON_AUDIO_EXTSr  r   r	   ACODECSKeyErrorr_   rr   r   rF  r   r   r9  rm   rn   rs   r  ry   r  time)r\   information	orig_pathrn   target_format	_skip_msg	filecodec	extensionr   rH  acodec	temp_pathnew_pathr1   r1   rB   r     s^   






zFFmpegExtractAudioPP.run)NNNF)rR   rS   rT   r   common_audiorQ  tuplerR  r   SUPPORTED_EXTSrC   	FORMAT_RErY   rF  r  r   _restrict_tor   r1   r1   r1   rB   r6    s    

r6  c                       s|   e Zd Zg eg ejdR eg ejddR R ZeeZ	dZ
d fdd	Zedd	 Zejd
ddd Z  ZS )FFmpegVideoConvertorPPgifr$   r;   
convertingNc                       t  | || _d S rX   superrY   rL   )r\   r]   preferedformat	__class__r1   rB   rY   "     
zFFmpegVideoConvertorPP.__init__c                 c   s,    t dE d H  | dkrdE d H  d S d S )NFavi)z-c:vlibxvidz-vtagXVIDrU   r   
target_extr1   r1   rB   _options&  s
   zFFmpegVideoConvertorPP._optionsFrK  c              	   C   s   |d |d   }}t|| j\}}|r(| d| j d| d|  g |fS t|||}| | j  d| d| d|  | ||| | ||d< | |d	< |d< |g|fS )
Nr   r   zNot z media file ""; z video from z to z; Destination: r?   )	rG   rP   rL   r  _ACTIONr   titler  rs  )r\   r   rk   
source_extrr  rX  outpathr1   r1   rB   r   ,  s   &
zFFmpegVideoConvertorPP.runNN)rR   rS   rT   sortedr   common_videor^  r`  rC   ra  ru  rY   r1  rs  r   rb  r   __classcell__r1   r1   rj  rB   rc    s    

rc  c                   @   s   e Zd ZdZedd ZdS )FFmpegVideoRemuxerPPremuxingc                 C   s   t  S rX   rp  rq  r1   r1   rB   rs  @  s   zFFmpegVideoRemuxerPP._optionsN)rR   rS   rT   ru  r1  rs  r1   r1   r1   rB   r}  =  s    r}  c                       s6   e Zd ZdZd	 fdd	Zejdddd Z  ZS )
FFmpegEmbedSubtitlePP)r   r   r%   r"   r'   r&   NFc                    rf  rX   )rh  rY   _already_have_subtitle)r\   r]   already_have_subtitlerj  r1   rB   rY   H  rl  zFFmpegEmbedSubtitlePP.__init__rK  c                 C   sf  |d | j vr| dd| j  d g |fS |d}|s(| d g |fS |d }	 |d }g g g }}}d}d}	| D ]i\}
}tj|dd	sY| d
|
 d qA|d }|dkrg| d n2|dkss|dkr|dkr|	|
 |	|d |	|d  n|s|dkr|dkrd}| d |	s|dkr|dkrd}	| d qA|sg |fS |g|}g | j
|d ddd}tt||ddD ]>\}\}
}|d|d  dg t|
p|
}|d| d| g |r|d| d| d| d| g qt|d }| d!| d" | ||| t|| | jr-g n|}||fS )#Nr   z"Subtitles can only be embedded in , z filesrequested_subtitlesz#There aren't any subtitles to embedr   Fr   Skipping embedding % subtitle because the file is missingr   z!JSON subtitles cannot be embeddedr"   r.   r   Tz3Only WebVTT subtitles can be embedded in webm filesr   asszEASS subtitles cannot be properly embedded in mp4 files; expect issuesr   r   z-0:sr(  r   z:0z-metadata:s:s:z	language=zhandler_name=title=rN  zEmbedding subtitles in "")r`  r  r@   rr   itemsrm   rn   rs   rt   r   r   r   r,  extendr   
short2longr   r   ry   r  )r\   r   	subtitlesrk   r   	sub_langs	sub_namessub_filenameswebm_vtt_warnmp4_ass_warnlangsub_infosub_extinput_filesr   r   r   	lang_codetemp_filenamefiles_to_deleter1   r1   rB   r   L  sp   






zFFmpegEmbedSubtitlePP.run)NF)	rR   rS   rT   r`  rY   r   rb  r   r|  r1   r1   rj  rB   r  E  s
    
r  c                   @   sR   e Zd ZdddZedd Zejddd	d
 Zedd Z	dd Z
dd ZdS )FFmpegMetadataPPT	if_existsc                 C   s"   t | | || _|| _|| _d S rX   )rU   rY   _add_metadata_add_chapters_add_infojson)r\   r]   add_metadataadd_chaptersadd_infojsonr1   r1   rB   rY     s   
zFFmpegMetadataPP.__init__c                 c   s2    | dk}t | E d H  |rdE d H  d S d S )Nr%   )rG  r8   r   rp  )rr  
audio_onlyr1   r1   rB   rs    s   zFFmpegMetadataPP._optionsFrK  c              	   C   sD  |  | |d d }}g g }}| jr.|dr.t|d}|| |d | || | jr9|| | | j	re|d dv r[|d}|| 
|| |sZ||d n
| j	du re| d |sp| d	 g |fS t|d
}| d| d | ||f|tj| |d g|R   | j|  t|| g |fS )Nr   r   metar   )r'   r&   infojson_filenameTz3The info-json can only be attached to mkv/mka fileszThere isn't any metadata to addrN  zAdding metadata to "r  )r   r  rr   r   r  _get_chapter_optsr   r  _get_metadata_optsr  _get_infojson_optsr  r   r   r  r  rs  r   rm   ry   )r\   r   rk   metadata_filenamer  optionsr  r  r1   r1   rB   r     s<   









zFFmpegMetadataPP.runc                 c   s    t |dddA}dd }d}| D ]+}|d7 }|d|d	 d
  7 }|d|d d
  7 }|d}|r<|d|| d7 }q|| W d    n1 sLw   Y  dV  d S )Nr  r  r  c                 S   s   t dd| S )Nz([\\=;#\n])z\\\1)r=   sub)r   r1   r1   rB   ffmpeg_escape  s   z9FFmpegMetadataPP._get_chapter_opts.<locals>.ffmpeg_escapez;FFMETADATA1
z[CHAPTER]
TIMEBASE=1/1000
z	START=%d

start_timei  zEND=%d
r   rv  r  r   )z-map_metadata1)r  rr   write)r   r  r%  r  metadata_file_contentchapterchapter_titler1   r1   rB   r    s   

z"FFmpegMetadataPP._get_chapter_optsc                 #   s2   dt td7 fdd	}|dd |dd |dd	 |d
d |dd |dd |dd |dd |dd |dd |dd |dd |d |dd |dd  d!| d"g v rp|d#d	 d$ d%d  t d&}  D ]"\}}t||}|d ur|r|	d'd(|
d)pd$ |
d*< q|d+V  d$  D ]\}}d,| d-| fV  qd.} d/p gD ]U}	d0|	d1|	d2fvrd3nd4}
t|	d5pd(p|	d5}t|||
 D ](}|rt| d5| t|  D ]\}}d6| | d-| fV  qq||
7 }qd S )8Nr  c                    sv   t  fdd dgt|p| D d }|dvr9dttt|}|dd}d tt| | d S d S )	Nc                 3   s&    | ]}  |d ur | V  qd S rX   )rr   )rg   key)r   r1   rB   rl     s    zCFFmpegMetadataPP._get_metadata_opts.<locals>.add.<locals>.<genexpr>r   )r   Nr   r   common)	rw   r   r@   mapstrry   updatedictfromkeys)	meta_list	info_listr   r   meta_prefixmetadatar1   rB   add  s   z0FFmpegMetadataPP._get_metadata_opts.<locals>.addrv  )trackrv  dateupload_date)descriptionsynopsisr  )purlcommentwebpage_urlr  track_numberartist)r  artistscreatorcreatorsuploaderuploader_idcomposer)r  	composersgenre)r  genres
categoriestagsalbum)r  seriesalbum_artist)r  album_artistsdiscdisc_numbershowr  season_number
episode_id)episoder  episode_sortepisode_numberzembed-metadatacompat_optsr  r  r  z(?P<i>\d+)?_(?P<key>.+)r  r   r   r  )z-write_id3v1r  z	-metadatar   r   requested_formatsnonevcodecr[  r   r   language-metadata:s:rX   )collectionsdefaultdictr  rp   popr=   escaper  	fullmatchry   r   rr   r   r  ranger  
setdefault)r\   r   r  
meta_regexr  r   r   r   
stream_idxfmtstream_countr  r   r1   r  rB   r    sV   















$ 
z#FFmpegMetadataPP._get_metadata_optsc                 c   s    |r	t j|sI| jdurd S |p&d| j|dp%t| j|d|d  }| j|s/d S | d|  t	| j
|| dd| ||d< | |d	 d
d\}}|d urddd| fV  |d8 }d| |d| dd| dfV  d S )NTz%s.tempinfojsonz	info.jsonr   zWriting info-json to: clean_infojsonr  r   )r  mimetypezapplication/jsonr   z-0:r   z-attachr  zmimetype=application/jsonzfilename=info.json)rm   rn   rs   r  _downloaderprepare_filenamer   _ensure_dir_existsr   r   sanitize_inforp   r   r   )r\   r   infofn
old_stream
new_streamr1   r1   rB   r    s*   




z#FFmpegMetadataPP._get_infojson_optsN)TTr  )rR   rS   rT   rY   r1  rs  r   rb  r   r  r  r  r1   r1   r1   rB   r    s    



!
<r  c                   @   s.   e Zd ZejZejdddd Zdd Z	dS )FFmpegMergerPPFrK  c           	      C   s   |d }t |d}ddg}d}t|d D ]F\}}|ddkrJ|d	| d
g |d do9| |d dk}|rF|d| dg |d7 }|ddkr[|d	| dg q| d| d | |d || t	|| |d |fS )Nr   rN  r   r   r   r  r[  r  r   z:a:0protocolm3u8r$   z-bsf:a:r4   r   r  z:v:0zMerging formats into "r  __files_to_merge)
r   r   rr   r  r   r   r  r   rm   rename)	r\   r   rk   r  r   audio_streamsr   r  	aac_fixupr1   r1   rB   r   0  s$   
 zFFmpegMergerPP.runc                 C   s   dS )NTr1   r   r1   r1   rB   	can_mergeD  s   zFFmpegMergerPP.can_mergeN)
rR   rS   rT   r   r{  r`  r   rb  r   r  r1   r1   r1   rB   r  -  s
    

r  c                   @   s   e Zd Zdd ZdS )FFmpegFixupPostProcessorc                 C   s>   t |d}| | d| d | ||| t|| d S )NrN  z of "r  )r   r  r  rm   ry   )r\   r   rk   r  r  r1   r1   rB   _fixupJ  s   
zFFmpegFixupPostProcessor._fixupN)rR   rS   rT   r  r1   r1   r1   rB   r  I  s    r  c                   @   "   e Zd Zejddddd ZdS )FFmpegFixupStretchedPPF)rL  audioc                 C   s@   | d}|dvr| d|d g |  d|d g |fS )Nstretched_ratior   zFixing aspect ratior   z-aspectr%  rr   r  r   )r\   r   r  r1   r1   rB   r   T  s   
zFFmpegFixupStretchedPP.runNrR   rS   rT   r   rb  r   r1   r1   r1   rB   r  S      r  c                   @   r  )FFmpegFixupM4aPPF)rL  videoc                 C   s8   | ddkr| d|d g |  dd g |fS )N	containerm4a_dashzCorrecting containerr   r2   r   r	  r\   r   r1   r1   rB   r   ^  s   "zFFmpegFixupM4aPP.runNr
  r1   r1   r1   rB   r  ]  r  r  c                   @   s(   e Zd Zdd Zejdddd ZdS )FFmpegFixupM3u8PPc              
   c   s    |d dv V  |d  dV  z	| |d }W n ty8 } z| d|j  dV  W Y d }~d S d }~ww t|dd	d
dkV  d S )Nr   )r   r%   r  r  r   zUnable to extract metadata: T)r?   format_nameFr   r    )r   r   r	   rt   r   r   )r\   r   r  r   r1   r1   rB   _needs_fixupf  s   zFFmpegFixupM3u8PP._needs_fixupFrK  c                 C   s\   t | |r*ddg}| |d dkr|ddg | d|d g |  | g |fS )Nr2   r   r   r$   r3   r4   zFixing MPEG-TS in MP4 container)allr  r   r  r  r   )r\   r   r   r1   r1   rB   r   q  s   zFFmpegFixupM3u8PP.runN)rR   rS   rT   r  r   rb  r   r1   r1   r1   rB   r  e  s    
r  c                       s2   e Zd Zd	 fdd	Zejdddd Z  ZS )
FFmpegFixupTimestampPPNMbP?c                    s,   t  | t|ttfsJ t|| _d S rX   )rh  rY   
isinstancerB  floatr  trim)r\   r]   r  rj  r1   rB   rY   ~  s   zFFmpegFixupTimestampPP.__init__FrK  c                 C   sZ   | j ds| d ddg}ng d}| d|d g || dd	| j g |fS )
Nr   zA re-encode is needed to fix timestamps in older versions of ffmpeg. Please install ffmpeg 4.4 or later to fixup without re-encodingz-vfzsetpts=PTS-STARTPTS)r   r   z-bsfzsetts=ts=TS-STARTPTSzFixing frame timestampr   F-ss)r_   rr   rt   r  r   r  )r\   r   r   r1   r1   rB   r     s   
*zFFmpegFixupTimestampPP.run)Nr  )rR   rS   rT   rY   r   rb  r   r|  r1   r1   rj  rB   r  |  s    
r  c                   @   s$   e Zd ZdZejdddd ZdS )FFmpegCopyStreamPPzCopying streamFrK  c                 C   s    |  | j|d |   g |fS )Nr   )r  MESSAGEr   r  r1   r1   rB   r     s   zFFmpegCopyStreamPP.runN)rR   rS   rT   r  r   rb  r   r1   r1   r1   rB   r    s    
r  c                   @      e Zd ZdZdS )FFmpegFixupDurationPPzFixing video durationNrR   rS   rT   r  r1   r1   r1   rB   r        r  c                   @   r  )FFmpegFixupDuplicateMoovPPzFixing duplicate MOOV atomsNr  r1   r1   r1   rB   r!    r   r!  c                       s,   e Zd ZejZd fdd	Zdd Z  ZS )FFmpegSubtitlesConvertorPPNc                    rf  rX   )rh  rY   r?   r\   r]   r?   rj  r1   rB   rY     rl  z#FFmpegSubtitlesConvertorPP.__init__c              	   C   s  | d}| j}|}|dkrd}|d u r| d g |fS | d g }| D ]\}}tj| dds@| d| d	 q(|d
 }||krR| d| d q(|dkr\| d q(|d }	||	 t	|	|}
|dv r| d |	}t	|	d}t
|d}t| }W d    n1 sw   Y  t
|ddd}|| W d    n1 sw   Y  |}	d||d||< |dkrq(|| | |	|
d|g t
|
dd}|| |
d||< W d    n1 sw   Y  t	|d |d  ||d |
< q(||fS )Nr  r.   r#   z%There aren't any subtitles to convertzConverting subtitlesr   r   r  r  r   zSubtitle file for z# is already in the requested formatr   zaYou have requested to convert json subtitles into another format, which is currently not possible)dfxpttmlttzpYou have requested to convert dfxp (TTML) subtitles into another format, which results in style information losssrtrbr  r  r  )r   datar   r2   __files_to_move)rr   r?   r  r  rm   rn   rs   rt   r   r   r  r   readr  r  )r\   r   subsnew_ext
new_formatr  r  r  r   old_filenew_file	dfxp_filesrt_filer%  srt_datar1   r1   rB   r     sr   







zFFmpegSubtitlesConvertorPP.runry  )	rR   rS   rT   r   r  r`  rY   r   r|  r1   r1   rj  rB   r"    s    r"  c                   @   s:   e Zd ZdddZdd Zdd Zejddd	d
 ZdS )FFmpegSplitChaptersPPFc                 C   s   t | | || _d S rX   )rU   rY   _force_keyframes)r\   r]   r  r1   r1   rB   rY     rl  zFFmpegSplitChaptersPP.__init__c                 C   s<   |  }|||d|d|dd | j|dS )Nrv  r  r   )section_numbersection_titlesection_startsection_endr  )r   r  rr   r  r  )r\   r   r  r   r1   r1   rB   _prepare_filename  s   z'FFmpegSplitChaptersPP._prepare_filenamec                 C   s`   |  |||}| j|sd S ||d< | d||f  |dt|d dt|d |d  gfS )Nr   zChapter %03d; Destination: %sr  r  z-tr   )r:  r  r  r  r  )r\   r   r  r   destinationr1   r1   rB   _ffmpeg_args_for_chapter  s   z.FFmpegSplitChaptersPP._ffmpeg_args_for_chapterrK  c                 C   s   |  | |dpg }|s| d g |fS |d }| jr/t|dkr/| |dd |D }| dt| d t|D ]\}}| |d ||\}}| ||fg|| 	 fg q>||d kri| j
|d d	 g |fS )
Nr   z"Chapter information is unavailabler   r   c                 s   s    | ]}|d  V  qdS )r  Nr1   )rg   cr1   r1   rB   rl     r  z,FFmpegSplitChaptersPP.run.<locals>.<genexpr>zSplitting video by chapters; z chapters found)r   )r   rr   r  r5  rI   r  r   r<  r   r   r   )r\   r   r   in_fileidxr  r;  r   r1   r1   rB   r   	  s   

zFFmpegSplitChaptersPP.runNF)	rR   rS   rT   rY   r:  r<  r   rb  r   r1   r1   r1   rB   r4    s    


r4  c                       s^   e Zd ZejZeeZd fdd	Ze	dd Z
dddZed	d
 Zdd Zdd Z  ZS )FFmpegThumbnailsConvertorPPNc                    rf  rX   rg  r#  rj  r1   rB   rY   !  rl  z$FFmpegThumbnailsConvertorPP.__init__c                 C   s&   t | j d| j d t|dkS )N.z.is_webp is deprecatedwebp)r   rS   rR   r   what)r-  rn   r1   r1   rB   is_webp%  s   z#FFmpegThumbnailsConvertorPP.is_webprF   c                 C   s   |d | d }t j|\}}|rK| dkrMt|dkrO| d| d t|d}t || ||d | d< t|d 	|d|d |< d S d S d S d S )N
thumbnailsr   z.webprC  zCorrecting thumbnail "z" extension to webpr*  )
rm   rn   splitextrG   r   rD  r  r   ry   r  )r\   r   r?  thumbnail_filenamer   thumbnail_extwebp_filenamer1   r1   rB   
fixup_webp*  s   
z&FFmpegThumbnailsConvertorPP.fixup_webpc                 c   s&    dE d H  | dkrdE d H  d S d S )N)z-updater  jpg)z-bsf:v
mjpeg2jpegr1   rq  r1   r1   rB   rs  6  s
   
z$FFmpegThumbnailsConvertorPP._optionsc                 C   sb   t ||}| d| d|  tj|\}}| ||dkr!g ng dfg|| |fg |S )NzConverting thumbnail "z" to z.gif)r2   image2z-pattern_typer  )r   r  rm   rn   rG  r   rs  )r\   rH  rr  thumbnail_conv_filenamer   rw  r1   r1   rB   convert_thumbnail<  s   
z-FFmpegThumbnailsConvertorPP.convert_thumbnailc           
      C   s   g }d}t |dpg D ]^\}}|d}|sqd}| || |d }tj|d dd   }|dkr9d}t|| j\}}	|	rO| 	d| d	|	  q| 
|||d< || t|d
 | ||d
 |d < q|ss| 	d ||fS )NFrF  r   Tr   jpegrL  zNot converting thumbnail "rt  r*  z&There aren't any thumbnails to convert)r   rr   rK  rm   rn   rG  rG   rP   rL   r  rP  r   r   )
r\   r   r  has_thumbnailr?  thumbnail_dictoriginal_thumbnailrI  rr  rX  r1   r1   rB   r   F  s0   


zFFmpegThumbnailsConvertorPP.runry  )rF   )rR   rS   rT   r   rF  r`  rC   ra  rY   r5  rE  rK  r1  rs  rP  r   r|  r1   r1   rj  rB   rA    s    



rA  c                       sH   e Zd Zd fdd	Zdd Z fddZejdddd	d
 Z  Z	S )FFmpegConcatPPFc                    s   || _ t | d S rX   )_only_multi_videorh  rY   )r\   r]   only_multi_videorj  r1   rB   rY   c  s   zFFmpegConcatPP.__init__c                 C   s.   t | |d}| dd|  t|S )N)r   .
codec_namez	Codecs = r  )r   r   r   r@   r_  )r\   r   codecsr1   r1   rB   _get_codecsg  s   zFFmpegConcatPP._get_codecsc                    s   | j |sd S t|dkr4tj|d tj|kr*| d|d  d| d t|d | g S ttt	| j
|dkrDtd| dt| d|  t || |S )	Nr   r   zMoving "z" to "r  zThe files have different streams/codecs and cannot be concatenated. Either select different formats or --recode-video them to a common formatzConcatenating z files; Destination: )r  r  rI   rm   rn   realpathr  ry   setr  rZ  r	   rh  r'  )r\   r!  r"  rj  r1   rB   r'  l  s   zFFmpegConcatPP.concat_files)rL  	simulatedc                 C   s   | dpg }t|r| jr|d dkrg |fS t|ddd fr%tdt|dp+g }t|t|k r8td	t|d
d}tdtt|dkrM|d ndi|| j	
|}| j	|d}| ||}||d dg|d< ||fS )Nentries_typemulti_video.c                 S   s   | dko	t |dkS )Nrequested_downloadsr   )rI   )r>  vr1   r1   rB   r     r   z$FFmpegConcatPP.run.<locals>.<lambda>zIConcatenation is not supported when downloading multiple separate formats).ra  r   r   z4Aborting concatenation because some downloads failed).ra  r   r   ).r   r   r   r   r'   pl_video)r   r   ra  )rr   anyrV  r   r	   rI   r  ChainMapr\  r  _playlist_infodictr  r'  )r\   r   r^  r!  extsie_copyr"  r  r1   r1   rB   r   ~  s$   "zFFmpegConcatPP.runr@  )
rR   rS   rT   rY   rZ  r'  r   rb  r   r|  r1   r1   rj  rB   rU  b  s    rU  ):r  r/  r3  r  r   rm   r=   r   rT  r  r   compatr   utilsr   r   r   r	   r
   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   EXT_TO_OUT_FORMATSrR  rC   rP   rQ   rU   r6  rc  r}  r  r  r  r  r  r  r  r  r  r  r!  r"  r4  rA  rU  r1   r1   r1   rB   <module>   sv    X  \j#Q 

	L/E