Ë
    ;éj?M  ã                   ó"  — 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 ddl	m
Z
  e
e«      j                  «       j                  Z ee«      ej                   vr"ej                   j#                  d ee«      «       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mZmZm Z  ejB                  Z!ejD                  Z" ee#dd¬	«      Z$d
e$j                  _%         ejL                  «       Z'i Z(i Z)dddœZ*d5de+fd„Z,de
fd„Z-defd„Z.d„ Z/e$ja                  d«      d„ «       Z1e$ja                  d«      d„ «       Z2e$jg                  d«      d„ «       Z4e$jg                  d«      d„ «       Z5e$jg                  d«      d„ «       Z6e$ja                  d«      d„ «       Z7e$ja                  d«      d„ «       Z8e$ja                  d «      d!„ «       Z9e$ja                  d"«      d#„ «       Z:e$jg                  d$«      d%„ «       Z;e$jg                  d&«      d'„ «       Z<e$ja                  d(«      d)„ «       Z=e$jg                  d*«      d+„ «       Z>e$jg                  d,«      d-„ «       Z?e$jg                  d.«      d/„ «       Z@d0„ ZAe$ja                  d1«      d2„ «       ZBd3„ ZCe#d4k(  r eC«        yy)6aÁ  
app: interfaz local de PlumLoom (Flask, una sola pagina).

    python Engine/ui/app.py            # http://127.0.0.1:5055
    python Engine/ui/app.py --port 8080

Habla DIRECTO con Forge (`127.0.0.1:7860`), pero la generacion la hace
`pack_builder.generate()` (via `runner`): la UI no reimplementa nada.

Flujo:
  /api/plan    compone los jobs y los guarda en memoria  -> preview (D2.7)
  /api/start   ejecuta EXACTAMENTE ese plan (hilo aparte) -> run_id
  /api/progress progreso en vivo (imagenes + log)
  /api/regen   regenera una imagen suelta (misma pose/camara, semilla nueva)
  /api/bank    ver / anadir / vetar poses (D2.3)

La UI nunca publica en Pixiv: solo lee tags (`pixiv_*`), nada de subir.
é    N)Údatetime)ÚPath)ÚFlaskÚjsonifyÚrender_templateÚrequestÚsend_from_directory)ÚSTAGESÚSTAGE_LEVELÚSTAGE_DRESSÚstaticÚ	templates)Ústatic_folderÚtemplate_folderFg        ©ÚokÚcheckedÚreturnc                 ó:  — t        j                   «       }| s!t        d   �|t        d   z
  dk  r	t        d   S d}	 ddl}|j                  dt        j
                  z  d¬	«      }|j                  d
k(  }t        j                  ||dœ«       |S # t        $ r d}Y Œ'w xY w)zGForge responde? Cache de 5 s (el debounce de la preview lo pide mucho).r   Nr   é   Fr   z%s/sdapi/v1/optionsg      ø?)ÚtimeoutéÈ   r   )	ÚtimeÚ_FORGEÚrequestsÚgetÚpbÚFORGEÚstatus_codeÚ	ExceptionÚupdate)ÚforceÚnowr   r   Úresps        úEngine\ui\app.pyÚforge_okr&   7   s›   € ä
�)‰)‹+€CÙ”V˜D‘\Ð-°#¼¸yÑ8IÑ2IÈAÒ2MÜ�d‰|ÐØ	€BðÛØ�|‰|Ð1´B·H±HÑ<Àcˆ|ÓJˆØ×Ñ Ñ$ˆô ‡M�M˜¨Ñ,Ô-Ø€Iøô ò ØŠðús   »7B ÂBÂBc                 óö   — | st        d«      ‚t        j                  «       }t        t        | «      z  j                  «       }||j                  vrt        d«      ‚|j                  «       st        d| z  «      ‚|S )z<Carpeta de un lote de la UI (solo dentro de Output/ui_runs).zfalta el lotezlote fuera de Output/ui_runszno existe el lote '%s')Ú
ValueErrorÚUI_RUNSÚresolveÚstrÚparentsÚis_dir)ÚnameÚrootÚpaths      r%   Ú_run_dirr1   G   sj   € áÜ˜Ó)Ð)Ü�?‰?Ó€DÜ”c˜$“iÑ×(Ñ(Ó*€DØ�4—<‘<ÑÜÐ7Ó8Ð8Ø�;‰;Œ=ÜÐ1°DÑ8Ó9Ð9Ø€Kó    c                  óD   — t        j                  «       j                  d d S )Né
   )ÚuuidÚuuid4Úhex© r2   r%   Ú_new_run_idr9   T   s   € Ü�:‰:‹<×Ñ˜C˜RÐ Ð r2   c                 ó¬   — | d   j                  t        j                  «       j                  d«      ›d|›�«       t	        | d   «      dkD  r	| d   d d…= y y )NÚlogz%H:%M:%Sz  é�  iÔþÿÿ)Úappendr   r#   ÚstrftimeÚlen)ÚstateÚtexts     r%   Ú_logrB   X   sP   € Ø	ˆ%�L×Ñ¤H§L¡L£N×$;Ñ$;¸JÕ$GÉÐNÔOÜ
ˆ5�‰<Ó˜3ÒØ�%‰L˜˜$˜Ñð r2   Ú/c                  ó   — t        d«      S )Nz
index.html)r   r8   r2   r%   ÚindexrE   `   s   € ä˜<Ó(Ð(r2   z	/api/metac                  ó<  — t        j                  «       } t        j                  «       }t        j                  | |«      }t        j                  | «      }t        j
                  | «      }t        dt        «       t        j                  dœt        t        «      ||t        D �cg c](  }|t         j                  |   t        |   t        |   dœ‘Œ* c}t!        t         j"                  «      |t!        t         j$                  «      dt!        t        «      dœdœ
«      S c c}w )NT)r   Úurl)ÚidÚtitleÚlevelÚdressé-   )ÚtotalÚstages)
r   ÚforgeÚbase_dirÚ
charactersÚthemesrN   ÚlevelsÚposesÚpack_presetsÚdefaults)ÚplannerÚload_contextÚused_charactersrQ   Úpose_countsÚthemes_metar   r&   r   r   r+   ÚBASE_DIRr
   ÚSTAGE_TITLEr   r   ÚlistÚLEVELSÚPACK_PRESETS)ÚctxÚusedÚcharsÚcountsrR   Úss         r%   Úapi_metarf   e   sí   € ä
×
Ñ
Ó
 €CÜ×"Ñ"Ó$€DÜ×Ñ˜s DÓ)€EÜ× Ñ  Ó%€FÜ× Ñ  Ó%€FÜØÜ ›
¬2¯8©8Ñ4Üœ“MØØõ #ó$á"�qð ¤g×&9Ñ&9¸!Ñ&<Ü(¨™^´kÀ!±nóFà"ñ$ô ”w—~‘~Ó&ØÜœW×1Ñ1Ó2Ø ¬D´«LÑ9ñó ð ùò$s   Â!-Dz	/api/planc                  ó¤  — t        j                  dd¬«      xs i } 	 t        j                  | «      }|d   }|d   }t        «       }t        t        j                  t        |«      «      |d<   t        5  |t        |<   t        t        «      d	kD  r>t        j                  t        t!        t        «      «      «       t        t        «      d	kD  rŒ>d d d «       d|d
<   ||d<   t#        |d   «      j$                  |d<   t'        «       |d<   t        |«      S # t        t
        f$ r#}t        dt        |«      dœ«      dfcY d }~S d }~ww xY w# 1 sw Y   Œ{xY w)NT©r"   ÚsilentF©r   Úerrorr<   ÚplanÚpreviewÚrun_diré   r   Úplan_idÚrun_namerO   )r   Úget_jsonrW   Úcomposer(   Ú
SystemExitr   r+   r9   Úunique_run_dirr)   ÚLOCKÚPLANSr?   ÚpopÚnextÚiterr   r.   r&   )ÚdataÚresultÚexcrl   rm   rp   s         r%   Úapi_planr~   ~   s  € ä×Ñ $¨tÔ4Ò:¸€Dð>Ü—‘ Ó&ˆð �&‰>€DØ�YÑ€GÜ‹m€Gäœ'×0Ñ0´¸'ÓBÓC€Dˆ�OÞ	ØŒˆg‰Ü”%‹j˜2ŠoÜ�I‰I”dœ4¤›;Ó'Ô(ô ”%‹j˜2‹o÷ 
ð
 €GˆD�MØ €GˆIÑÜ˜t I™Ó/×4Ñ4€GˆJÑÜ“z€GˆGÑÜ�7ÓÐøô# œ
Ð#ò >Ü˜e¬c°#«hÑ7Ó8¸#Ð=Õ=ûð>ú÷ 
ˆús*   �D Á2AEÄEÄ D>Ä8EÄ>EÅEz
/api/startc                  ó  ‡‡	‡
— t        j                  dd¬«      xs i } | j                  d«      }t        j                  |«      Š	‰	st	        dddœ«      dfS t        d¬«      s!t	        dd	t        j                  z  dœ«      dfS t        «       }t        ‰	d
   «      }|j                  «       rz|j                  }d}|j                  d||fz  z  j                  «       r(|dz  }|j                  d||fz  z  j                  «       rŒ(|j                  d||fz  z  }t        |«      ‰	d
<   t        d„ ‰	d   D «       «      }i d|“dd“dd“d|“d
‰	d
   “d|j                  “d|“dd“dd“dd“dd “dg “dg “dd “dd “d t        j                  «       “d!d “Š
t         5  ‰
t"        |<   d d d «       t%        ‰
d"|‰
d   fz  «       ˆ
fd#„Šˆˆ	ˆ
fd$„}t'        j(                  |d¬%«      j+                  «        t	        d|‰
d   |d&œ«      S # 1 sw Y   ŒaxY w)'NTrh   rp   Fz%plan caducado: vuelve a previsualizarrj   é™  ©r"   z.Forge no responde en %s (webui-user.bat --api)rn   é   z%s_%dé   c              3   ó8   K  — | ]  }t        |d    «      –— Œ y­w)ÚjobsN)r?   )Ú.0Úitems     r%   Ú	<genexpr>zapi_start.<locals>.<genexpr>¯   s   è ø€ Ð<©m d”�D˜‘L×!©mùs   ‚ÚitemsÚrun_idÚkindÚbatchr@   Úrunningrq   rM   Údoner   ÚfailedÚstopÚcurrentÚimagesr;   Úsummaryrk   ÚstartedÚfinishedzlanzando %d imagenes en %sc                 óÀ  •— | j                  d«      }t        5  |dk(  r!t        ‰d| d   | d   | d   | d   fz  «       �n|dk(  rH| j                  d«      | j                  d	«      | j                  d
«      | j                  d«      dœ‰d<   �n¾|dk(  �rHd| v �rC| d   }| j                  d«      }| j                  d«      xs |}‰dxx   dz  cc<   d ‰d<   ‰d   j                  ||›d|j                  d«      ›�|j                  d	«      |j                  d
«      |j                  d«      |j                  d«      |j                  d«      |j                  d«      |j                  d«      dœ	«       t        ‰d‰d   ‰d   | j                  d«      |j                  d	«      xs |j                  d
«      |j                  d«      |j                  d«      fz  «       np|dk(  rP‰dxx   dz  cc<   t        ‰d| j                  d«      ›d| j                  d«      ›d| j                  d«      ›�«       n|dk(  rd | v rt        ‰d!| d    z  «       d d d «       y # 1 sw Y   y xY w)"NÚeventÚ
char_startz!personaje %d/%d: %s (%d imagenes)rE   rM   Úcharr’   ÚstartÚstageÚnivelÚpose_id)r™   r›   rœ   r�   r‘   rŽ   ÚrecordÚdirrƒ   rC   ÚfileÚseedÚcamerarK   Útheme)	r™   r    r›   rœ   r�   r¡   r¢   rK   r£   z%d/%d %s %s %s (seed %s)Úfailr�   zFALLO Ú z: rk   Ú	generatedzlote terminado: %d imagenes)r   rv   rB   r=   )Úevr‹   Úrecr™   Úfolderr@   s        €r%   Úon_eventzapi_start.<locals>.on_event¼   s,  ø€ Ø�v‰v�g‹ˆÞØ�|Ò#Ü�UÐ?Ø˜7™ R¨¡[°"°V±*¸bÀ¹lÐKñLö Mà˜’Ø,.¯F©F°6«NØ-/¯V©V°G«_Ø-/¯V©V°G«_Ø/1¯v©v°iÓ/@ñ$B��iÓ ð ˜“ H°¢NØ˜‘l�Ø—v‘v˜f“~�ØŸ™ ›Ò.¨$�Ø�f“ Ñ"“Ø#'��iÑ Ø�h‘×&Ñ&Ø ò (.¨s¯w©w°v¬Ð?Ø ŸW™W WÓ-¸¿¹ÀÓ8HØ"Ÿw™w yÓ1¸3¿7¹7À6»?Ø!Ÿg™g hÓ/¸#¿'¹'À'Ó:JØ ŸW™W WÓ-ñ
(ô 
ô �UÐ6Ø˜f™ u¨W¡~°r·v±v¸f³~ØŸ™ Ó(Ò<¨C¯G©G°GÓ,<ØŸ™ 	Ó*¨C¯G©G°F«Oð=ñ=õ >ð ˜’Ø�h“ 1Ñ$“Ü‘UØŸ™˜v�¨¯©¨yÕ(9¸2¿6¹6À'¼?ðLõ Mà˜’ K°2Ñ$5Ü�UÐ9¸B¸{¹OÑKÔL÷G �T‰Tús   ™H2IÉIc                  óÆ  •— 	 t        j                  ‰‰ˆfd„¬«      } t        5  | ‰d<   | j                  d«      rdnd‰d<   t	        j                  «       ‰d<   d ‰d	<   d d d «       y # 1 sw Y   y xY w# t
        $ rd}t        5  d
‰d<   t        |«      ‰d
<   t	        j                  «       ‰d<   t        ‰d|z  «       d d d «       n# 1 sw Y   nxY wY d }~y Y d }~y d }~ww xY w)Nc                  ó(   •— ‰ j                  dd«      S )Nr�   F©r   )r@   s   €r%   Ú<lambda>z+api_start.<locals>.worker.<locals>.<lambda>ç   s   ø€  E§I¡I¨f°eÔ$<r2   )rª   Úshould_stopr“   ÚstoppedÚ	cancelledrŽ   r@   r•   r‘   rk   ú	ERROR: %s)ÚrunnerÚrun_planrv   r   r   r    r+   rB   )r“   r}   rª   rl   r@   s     €€€r%   Úworkerzapi_start.<locals>.workerã   sÂ   ø€ ð	/Ü—o‘oØ˜xÛ<ô>ˆGö Ø#*��iÑ Ø18·±¸YÔ1G¡+Ø'-ð �g‘ä$(§I¡I£K��jÑ!Ø#'��iÑ ÷ —‘ûô ò 	/ÞØ!(��g‘Ü!$ S£��g‘Ü$(§I¡I£K��jÑ!Ü�U˜K¨#Ñ-Ô.÷	 —‘ú—‘ûð	/úsL   ƒ!A3 ¤:A'ÁA3 Á'A0Á,A3 Á0A3 Á3	C Á<CÂ:CÂ<	CÃC	Ã
CÃC ©ÚtargetÚdaemon)r   rŠ   rq   rM   )r   rr   r   rw   r   r&   r   r   r9   r   Úexistsr.   Úparentr+   Úsumr   rv   ÚRUNSrB   Ú	threadingÚThreadrš   )r{   rp   rŠ   rn   ÚbaseÚnrM   rµ   rª   rl   r@   s           @@@r%   Ú	api_startrÁ   —   s™  ú€ ä×Ñ $¨tÔ4Ò:¸€DØ�h‰h�yÓ!€GÜ�9‰9�WÓ€DÙÜ˜eð /=ñ >ó ?Ø@CðDð 	Dä˜$ÕÜ˜eð /Fä/1¯x©xñ/8ñ 9ó :à;>ð?ð 	?ô ‹]€Fô �4˜	‘?Ó#€GØ‡~�~ÔØ�|‰|ˆØˆØ�~‰~ ¨D°!¨9Ñ!4Ñ5×=Ñ=Ô?Ø�‰FˆAð �~‰~ ¨D°!¨9Ñ!4Ñ5×=Ñ=Õ?à—.‘. G¨t°Q¨iÑ$7Ñ8ˆÜ˜g›,ˆˆY‰ÜÑ<¨d°7ªmÓ<Ó<€EðØ�&ðØ  'ðØ+2°Iðà�7ðà% t¨I¡ðð 	�G—L‘Lðð 	�ð	ð  ð	ð $,¨Qð	ð 17¸ð	ð
 	�4ðð
 " 2ðð
 (-¨bðð
 3<¸Tðð 	�ðð !¤$§)¡)£+ðð 0:¸4ð€Eö 
ØŒˆV‰÷ 
äˆÐ,°°u¸ZÑ7HÐ/IÑIÔJô%MöN/ô$ ×Ñ˜F¨4Ô0×6Ñ6Ô8Ü˜$¨&Ø % jÑ 1¸EñCó Dð D÷} 
ˆús   Æ
G?Ç?Hz	/api/stopc                  óà   — t        j                  dd¬«      xs i } t        j                  | j                  d«      «      }|st	        dddœ«      dfS d|d<   t        |d	«       t	        d
di«      S )NTrh   rŠ   Fúrun desconocidorj   é”  r�   z-cancelacion pedida (acaba la imagen en curso)r   )r   rr   r¼   r   r   rB   )r{   r@   s     r%   Úapi_stoprÅ   ú   sl   € ä×Ñ $¨tÔ4Ò:¸€DÜ�H‰H�T—X‘X˜hÓ'Ó(€EÙÜ˜eÐ.?Ñ@ÓAÀ3ÐFÐFØ€Eˆ&�MÜˆÐ?Ô@Ü�D˜$�<Ó Ð r2   z/api/progressc                  ól  — t         j                  j                  d«      } t        j                  | «      }|st	        dddœ«      dfS t
        5  |j                  «       D ��ci c]  \  }}|dk7  sŒ||“Œ }}}|d   dd  |d<   d|d	<   d d d «       t	        |«      S c c}}w # 1 sw Y   t	        «      S xY w)
NrŠ   FrÃ   rj   rÄ   r;   i°ÿÿÿTr   )r   Úargsr   r¼   r   rv   r‰   )rŠ   r@   ÚkÚvÚpayloads        r%   Úapi_progressrË     s°   € ä�\‰\×Ñ˜hÓ'€FÜ�H‰H�VÓ€EÙÜ˜eÐ.?Ñ@ÓAÀ3ÐFÐFÞ	Ø$)§K¡K¤MÔ@¡M™D˜A˜q°Q¸%³Z�1�a‘4 MˆÑ@Ø˜u™ c dÐ+ˆ�‰Øˆ�‰÷ 
ô �7ÓÐùó A÷ 
ô �7ÓÐús$   ÁB Á!BÁ/BÁ4B ÂB Â B3z	/api/runsc            
      óü  — g } t         j                  «       �r0t        t         j                  «       d¬«      D ]ú  }|j	                  «       sŒ|dz  }|j                  «       sŒ*	 t        j                  |j                  d¬«      «      }t        |D �ch c]H  }|j                  d«      s|j                  d«      r$|j                  d«      xs |j                  d«      ’ŒJ c}«      }| j                  |j                  t        |«      t        |«      |j                  «       j                  |d d d	œ«       Œü | j!                  d
„ d¬«       t#        d| d d dœ«      S # t        t
        j                  f$ r Y �Œ>w xY wc c}w )NT)Úreverseúmanifest_all.jsonúutf-8©Úencodingr™   Úchar_diré   )r.   r’   rc   ÚmtimeÚ
chars_listc                 ó   — | d   S )NrÔ   r8   )Úrs    r%   r®   zapi_runs.<locals>.<lambda>+  s   € ˜q šzr2   )ÚkeyrÍ   é   )r   Úruns)r)   r¹   ÚsortedÚiterdirr-   ÚjsonÚloadsÚ	read_textÚOSErrorÚJSONDecodeErrorr   r=   r.   r?   ÚstatÚst_mtimeÚsortr   )Úoutr0   ÚmanÚrecordsr×   rc   s         r%   Úapi_runsrè     sM  € à
€CÜ‡~�~ÕÜœ7Ÿ?™?Ó,°d×;ˆDØ—;‘;”=ØØÐ,Ñ,ˆCØ—:‘:”<ØðÜŸ*™* S§]¡]¸G ]Ó%DÓE�ô Ù%,óVÙ%, °·±°v´À!Ç%Á%È
ÔBSð ŸE™E &›MÒ>¨Q¯U©U°:Ó->Ñ>Ø%,ñVó WˆEà�J‰JØŸ	™	Ü˜g›,Ü˜U›ØŸ™›×,Ñ,Ø# B Q˜iñõ ð <ð& 	�‰Ñ)°4ˆÔ8Ü˜$¨¨C¨R¨Ñ1Ó2Ð2øô œT×1Ñ1Ð2ò ÚðüòVs   Á"%EÂAE9
ÅE6Å5E6z/api/run/<name>c                 ó  — 	 t        | «      }g d }}	 t	        j
                  |dz  j                  d¬«      «      }	 t	        j
                  |dz  j                  d¬«      «      }t        d„ |j                  d	«      D «       «      }t        d
| |||dœ«      S # t        $ r#}t        dt        |«      dœ«      dfcY d }~S d }~ww xY w# t        t        j                  f$ r g }Y Œ§w xY w# t        t        j                  f$ r d }Y ŒŸw xY w)NFrj   rÄ   rÎ   rÏ   rÐ   z	plan.jsonc              3   ó4   K  — | ]  }|j                   –— Œ y ­w)N)r.   )r†   Úps     r%   rˆ   zapi_run.<locals>.<genexpr>?  s   è ø€ Ð:Ñ$9˜q�A—F•FÑ$9ùs   ‚z*.jpgT)r   r.   rç   rl   Úsheets)r1   r(   r   r+   rÝ   rÞ   rß   rà   rá   rÛ   Úglob)r.   rn   r}   rç   rl   rì   s         r%   Úapi_runrî   /  s  € ð>Ü˜4“.ˆð ˜ˆT€GðÜ—*‘*˜gÐ(;Ñ;×FÑFØð Gó ó ˆðÜ�z‰z˜7 [Ñ0×;Ñ;ÀWÐ;ÓMÓNˆô Ñ: G§L¡L°Ô$9Ó:Ó:€FÜ˜$¨¸Ø ¨Fñ4ó 5ð 5øô ò >Ü˜e¬c°#«hÑ7Ó8¸#Ð=Õ=ûð>ûô ”T×)Ñ)Ð*ò ØŠðûô ”T×)Ñ)Ð*ò ØŠðús?   ‚B ’(C »(C% Â	CÂB<Â6CÂ<CÃC"Ã!C"Ã%DÄDz/api/image/<name>/<path:rel>c                 óp   — 	 t        | «      }t        ||«      S # t        $ r t        dddœ«      dfcY S w xY w)NFzlote desconocidorj   rÄ   )r1   r(   r   r	   )r.   Úrelrn   s      r%   Ú	api_imagerñ   D  sI   € ðHÜ˜4“.ˆô ˜w¨Ó,Ð,øô ò HÜ˜eÐ.@ÑAÓBÀCÐGÒGðHús   ‚ ™5´5z	/api/openc                  ó6  — t        j                  dd¬«      xs i } 	 t        | j                  d«      «      }t	        j
                  t        |«      «       t        dt        |«      dœ«      S # t        $ r#}t        dt        |«      dœ«      dfcY d }~S d }~ww xY w)NTrh   ÚrunFrj   r<   )r   r0   )	r   rr   r1   r   ÚosÚ	startfiler+   r    r   )r{   rn   r}   s      r%   Úapi_openrö   M  s�   € ä×Ñ $¨tÔ4Ò:¸€Dð>Ü˜4Ÿ8™8 E›?Ó+ˆÜ
�‰”S˜“\Ô"ô ˜$¬¨G«Ñ5Ó6Ð6øô ò >Ü˜e¬c°#«hÑ7Ó8¸#Ð=Õ=ûð>ús   �8A, Á,	BÁ5BÂBÂBz
/api/regenc            	      óÚ  ‡‡‡‡— t        j                  dd¬«      xs i Š	 t        ‰j                  d«      «      Št        d¬«      s!t        ddt        j                  z  dœ«      d	fS t        «       }i d
|“dd“dd“dt        ‰«      “d‰j                  “dd“dd“dd“dd“dd “dg “dg “dd “dd “dt        j                  «       “dd “d‰j                  d«      ‰j                  d «      ‰j                  d!«      ‰j                  d"«      d#œ“Št        5  ‰t        |<   d d d «       t        ‰d$‰j                  d«      ›d%‰j                  d"«      ›�«       ‰j                  d&«      Š‰d'vrt!        ‰«      nd Šˆˆˆˆfd(„}t#        j$                  |d¬)«      j'                  «        t        d|d*œ«      S # t        $ r#} t        dt        | «      dœ«      dfcY d } ~ S d } ~ ww xY w# 1 sw Y   ŒÅxY w)+NTrh   ró   Frj   r<   r�   zForge no responde en %sr€   rŠ   r‹   Úregenr@   r�   rn   rq   rM   rƒ   rŽ   r   r�   r�   r‘   r’   r;   r“   rk   r”   r•   r·   r™   r�   r›   r    )r™   r�   r›   r    zregenerando r¥   r¡   )NÚ c                  ó´  •— 	 t        j                  ‰‰j                  d«      ‰j                  d«      ‰j                  d«      ‰j                  d«      ‰‰j                  d«      xs d ¬«      } t        5  d‰d<   d	‰d<   | ‰d
<   t	        j                  «       ‰d<   | d   | d   | d   | d   | d   | d   | d   | d   dœg‰d<   t        ‰d| d   ›d| d   ›d| d   rdnd›�«       t        j                  «       D ]Y  }|j                  dg «      D ]B  }|j                  d«      | d   k(  sŒ|j                  d«      | d   k(  sŒ3| d   |d<   | d   |d<   ŒD Œ[ 	 d d d «       y # 1 sw Y   y xY w# t        $ rd}t        5  d‰d<   t        |«      ‰d<   t	        j                  «       ‰d<   t        ‰d|z  «       d d d «       n# 1 sw Y   nxY wY d }~y Y d }~y d }~ww xY w)Nr™   r�   r›   r    Ú	neg_extra)r�   r›   r    r¡   rû   rŽ   r@   rƒ   r“   r•   Únew_filerœ   r¡   r¢   rK   )r™   r    r›   rœ   r�   r¡   r¢   rK   r’   znueva imagen z (seed Ú)Údriftz  [ojo: el prompt cambio]rù   Úold_filerk   r²   )
r³   Ú	regen_oner   rv   r   rB   r¼   Úvaluesr    r+   )r|   ÚotherÚimgr}   r{   rn   r¡   r@   s       €€€€r%   rµ   zapi_regen.<locals>.workerv  sÓ  ø€ ð!	/Ü×%Ñ%Ø˜Ÿ™ &Ó)°4·8±8¸IÓ3FØ—h‘h˜wÓ'¨d¯h©h°vÓ.>ÀTØŸ(™( ;Ó/Ò7°4ô9ˆFö Ø!'��g‘Ø !��f‘Ø#)��iÑ Ü$(§I¡I£K��jÑ!Ø,2°6©NØ,2°:Ñ,>Ø-3°G©_Ø-3°G©_Ø/5°iÑ/@Ø,2°6©NØ.4°XÑ.>Ø-3°G©_ñ$>ð #?��h‘ô ‘UØ˜zÓ*¨F°6«NØ7=¸g²Ñ3ÈBÐNðPô Qô "Ÿ[™[ž]�EØ$Ÿy™y¨°2Ö6˜ØŸG™G F›O¨v°f©~Ó=Ø$'§G¡G¨F£O°v¸jÑ7IÓ$IØ*0°Ñ*<˜C ™KØ*0°©.˜C šKñ	  7ñ +÷# —‘ûô. ò 	/ÞØ!(��g‘Ü!$ S£��g‘Ü$(§I¡I£K��jÑ!Ü�U˜K¨#Ñ-Ô.÷	 —‘ú—‘ûð	/ús[   ƒA1E* Á4B3EÄ(EÅ EÅE* ÅE'Å#E* Å'E* Å*	GÅ3GÅ9:F<Æ3	GÆ<G	ÇGÇGr¶   )r   rŠ   )r   rr   r1   r   r(   r   r+   r&   r   r   r9   r.   r   rv   r¼   rB   Úintr½   r¾   rš   )r}   Úregen_idrµ   r{   rn   r¡   r@   s      @@@@r%   Ú	api_regenr  Z  s1  û€ ä×Ñ $¨tÔ4Ò:¸€Dð>Ü˜4Ÿ8™8 E›?Ó+ˆô ˜$ÕÜ˜eÐ.GÜ/1¯x©xñ/8ñ 9ó :Ø;>ð?ð 	?ô ‹}€HðØ�(ðØ" GðØ-4°iðà”3�w“<ðà!+¨W¯\©\ðð 	�ðð ˜Aðð  (¨ðð -3°Eðð <EÀdðð 	�"ð	ð ˜Rð	ð "+¨Dð	ð 3:¸4ð	ð
 	”4—9‘9“;ðð
 !+¨Dðð 	˜4Ÿ8™8 FÓ+¸¿¹ÀÓ8KØ ŸH™H WÓ-°t·x±xÀÓ7GñIð€Eö 
ØŒˆX‰÷ 
ä‰ t§x¡x°Õ'7¸¿¹À&Ô9IÐJÔKà�8‰8�FÓ€DØ JÑ.Œ3ˆtŒ9°D€D÷"/ôH ×Ñ˜F¨4Ô0×6Ñ6Ô8Ü˜$¨(Ñ3Ó4Ð4øôy ò >Ü˜e¬c°#«hÑ7Ó8¸#Ð=Õ=ûð>ú÷  
ˆús)   ¡F2 Ä
G!Æ2	GÆ;GÇGÇGÇ!G*z	/api/bankc                  ó`  — t        j                  «       } | d   }g }| d   D ]Ó  }|j                  |j                  d«      |j                  d«      |j                  d«      |j                  d«      xs g |j                  d«      t	        j
                  |j                  dd«      |«      |j                  t	        j                  |j                  dd«      «      «      xs i j                  d	«      d
œ«       ŒÕ t        d|t        j                  | «      t	        j                  | d   «      dœ«      S )NÚavoidÚbankrH   rœ   Ú	pose_lineÚtemaÚ
provenancerù   Úmotivo)rH   rœ   r
  r  r  Úavoidedr  T)r   rT   rd   Ústats)
rW   rX   r=   r   Ú	pose_bankÚ
is_avoidedÚnormalize_keyr   rZ   r  )ra   r  rT   Úentrys       r%   Úapi_bankr     s  € ä
×
Ñ
Ó
 €CØ�‰L€EØ€EØ�V”ˆØ�‰Ø—)‘)˜D“/Ø—Y‘Y˜wÓ'ØŸ™ ;Ó/Ø—I‘I˜fÓ%Ò+¨ØŸ)™) LÓ1Ü ×+Ñ+¨E¯I©I°kÀ2Ó,FÈÓNØ—y‘y¤×!8Ñ!8Ø—	‘	˜+ rÓ*ó",ó -ò 3Ø02·C±C¸³Mñ	
õ 		ð ô ˜$¨Ü%×1Ñ1°#Ó6Ü&Ÿ_™_¨S°©[Ó9ñ;ó <ð <r2   z/api/bank/addc                  ó¢  ‡— t        j                  dd¬«      xs i } | j                  d«      xs dj                  «       }| j                  d«      xs dj                  «       }|st	        dddœ«      d	fS |t
        j                  vrt	        dd
dœ«      d	fS t        j                  |«      rt	        dddœ«      d	fS t        j                  «       }t        j                  |«      Št        ˆfd„|D «       d «      }|r"t	        dd|j                  d«      z  dœ«      dfS | j                  d«      xs g }t        |t        «      r=|j                  d«      D �cg c]#  }|j                  «       sŒ|j                  «       ‘Œ% }}t        j                  |||d dd dd| j                  d«      xs dj                  «       «	      }t	        d|dœ«      S c c}w )NTrh   r
  rù   rœ   Fzla pose esta vaciarj   r<   znivel invalidoz(esa pose esta vetada; reactivala primeroc              3   ót   •K  — | ]/  }t        j                  |j                  d d«      «      ‰k(  sŒ,|–— Œ1 y­w)r
  rù   N)r  Ú	signaturer   )r†   ÚeÚsigs     €r%   rˆ   zapi_bank_add.<locals>.<genexpr>Ã  s7   øè ø€ ð (™D�q¤I×$7Ñ$7Ø	�‰ˆk˜2Óó% Ø#&ó%'”™Dùs   ƒ-8±8zya existe como %srH   r€   r  Ú,Úuig      ð?Únotas)r   rH   )r   rr   r   Ústripr   rW   r_   r  r  Ú	load_bankr  ry   Ú
isinstancer+   ÚsplitÚadd_pose)	r{   Úlinerœ   r	  Úduper  ÚtÚnew_idr  s	           @r%   Úapi_bank_addr&  µ  sÃ  ø€ ä×Ñ $¨tÔ4Ò:¸€DØ�H‰H�[Ó!Ò' R×.Ñ.Ó0€DØ�X‰X�gÓÒ$ "×+Ñ+Ó-€EÙÜ˜eÐ.BÑCÓDÀcÐIÐIØ”G—N‘NÑ"Ü˜eÐ.>Ñ?Ó@À#ÐEÐEÜ×Ñ˜DÔ!Ü˜eð /Bñ Có DØEHðIð 	Iä×ÑÓ €DÜ
×
Ñ
˜dÓ
#€CÜó (™Dó (Ø)-ó/€DáÜ˜eØ!4°t·x±xÀ³~Ñ!EñGó HØILðMð 	Mà�8‰8�FÓÒ!˜r€DÜ�$œÔØ#'§:¡:¨c¤?Ó@¡?˜a°a·g±gµi�—‘•	 ?ˆÐ@Ü×Ñ  e¨T°4¸¸TÀ4Ø # d§h¡h¨wÓ&7Ò&=¸2×%DÑ%DÓ%FóH€Fä˜$ fÑ-Ó.Ð.ùò As   ÅGÅ,Gz/api/bank/blacklistc                  ó  — t        j                  dd¬«      xs i } t        | «      }|st        dddœ«      dfS t	        j
                  || j                  d«      xs dj                  «       «      }t        d|d	   d
œ«      S )NTrh   Fúpose no encontradarj   rÄ   r  zvetada desde la UIrØ   )r   rØ   )r   rr   Ú_pose_line_from_requestr   r  Ú	blacklistr   r  )r{   r"  Úrows      r%   Úapi_bank_blacklistr,  Ð  s|   € ä×Ñ $¨tÔ4Ò:¸€DÜ" 4Ó(€DÙÜ˜eÐ.BÑCÓDÀcÐIÐIÜ
×
Ñ
˜d T§X¡X¨hÓ%7ò &:Ø%9¿5¹5»7óD€Cä˜$ s¨5¡zÑ2Ó3Ð3r2   z/api/bank/unblacklistc                  óÖ   — t        j                  dd¬«      xs i } t        | «      }|st        dddœ«      dfS t	        j
                  |«      st        dddœ«      dfS t        ddi«      S )	NTrh   Fr(  rj   rÄ   zno estaba vetadar   )r   rr   r)  r   r  Úunblacklist)r{   r"  s     r%   Úapi_bank_unblacklistr/  Û  so   € ä×Ñ $¨tÔ4Ò:¸€DÜ" 4Ó(€DÙÜ˜eÐ.BÑCÓDÀcÐIÐIÜ× Ñ  Ô&Ü˜eÐ.@ÑAÓBÀCÐGÐGÜ�D˜$�<Ó Ð r2   c                 óÌ   ‡ — ‰ j                  d«      r‰ d   S ‰ j                  d«      r<t        ˆ fd„t        j                  «       D «       d «      }|r|j                  d«      S d S y )Nr
  rH   c              3   óP   •K  — | ]  }|j                  d «      ‰d    k(  r|–— Œ y­w)rH   Nr­   )r†   r  r{   s     €r%   rˆ   z*_pose_line_from_request.<locals>.<genexpr>ê  s-   øè ø€ ð 4Ñ!6˜AØŸ™˜t›¨¨T©
Ò2ô Ñ!6ùs   ƒ#&)r   ry   r  r  )r{   r  s   ` r%   r)  r)  æ  s`   ø€ Ø‡x�x�ÔØ�KÑ Ð Ø‡x�x�„~Üó 4¤×!4Ñ!4Ô!6ó 4Ø59ó;ˆá).ˆu�y‰y˜Ó%Ð8°DÐ8Ør2   z/api/hashtags-dbc                  ó  — t         dz  dz  } | j                  «       st        i «      S 	 t        j                  | j                  d¬«      «      }t        |«      S # t        $ r"}t        dt        |«      i«      dfcY d }~S d }~ww xY w)NÚArchivoszcharacter_hashtags_db.jsonrÏ   rÐ   rk   iô  )r\   r¹   r   rÝ   rÞ   rß   r    r+   )rë   r{   r  s      r%   Úapi_hashtags_dbr4  ò  sv   € ä�:ÑÐ <Ñ<€AØ�8‰8Œ:Ü�r‹{Ðð/Ü�z‰z˜!Ÿ+™+¨w˜+Ó7Ó8ˆÜ�t‹}ÐøÜò /Ü˜¤ Q£Ð(Ó)¨3Ð.Õ.ûð/ús   ©/A Á	BÁ"A?Á9BÁ?Bc            
      óX  — t        j                  d¬«      } | j                  dt        j                  j                  dd«      ¬«       | j                  dt        t        t        j                  j                  dd	«      «      ¬
«       | j                  dd¬«       | j                  «       }t        d|j                  |j                  t        j                  fz  «       t        d¬«      st        d«       t        j                  |j                  |j                  |j                   d¬«       y )NzUI local de PlumLoom)Údescriptionz--hostÚPLUMLOOM_UI_HOSTz	127.0.0.1)Údefaultz--portÚPLUMLOOM_UI_PORTÚ5055)Útyper8  z--debugÚ
store_true)Úactionz#[-] UI en http://%s:%d  (Forge: %s)Tr�   zB[!] Forge no responde ahora mismo: la preview funciona, lanzar no.)ÚhostÚportÚdebugÚthreaded)ÚargparseÚArgumentParserÚadd_argumentrô   Úenvironr   r  Ú
parse_argsÚprintr>  r?  r   r   r&   Úappró   r@  )rë   rÇ   s     r%   ÚmainrI     sà   € Ü×ÑÐ,BÔC€AØ‡N�N�8¤R§Z¡Z§^¡^Ð4FØ4?ó&A€Nô Bà‡N�N�8¤#ÜœrŸz™zŸ~™~Ð.@À&ÓIÓJð ô Là‡N�N�9 \€NÔ2Ø�<‰<‹>€DÜ	Ð
/°4·9±9¸d¿i¹iÜ35·8±8ð3=ñ =ô >ä˜$ÕÜð ô 	ä‡G�G�—‘ §¡°$·*±*Àt€GÕLr2   Ú__main__)F)DÚ__doc__rB  rÝ   rô   Úsysr½   r   r5   r   Úpathlibr   Ú__file__r*   rº   ÚHEREr+   r0   ÚinsertÚflaskr   r   r   r   r	   rW   r³   r  Úpack_builderr   rN   r
   r   r   r\   r)   Ú__name__rH  Úensure_asciiÚLockrv   rw   r¼   r   Úboolr&   r1   r9   rB   r   rE   rf   Úpostr~   rÁ   rÅ   rË   rè   rî   rñ   rö   r  r  r&  r,  r/  r)  r4  rI  r8   r2   r%   Ú<module>rX     sñ  ðñó$ Û Û 	Û 
Û Û Û Ý Ý áˆHƒ~×ÑÓ×&Ñ&€Ù€tƒ9�C—H‘HÑØ‡H�H‡O�O�A‘s˜4“yÔ!ç OÕ Oã Û Û Û ß 3Ñ 3à×Ñ€Ø
�.‰.€áˆH H¸kÔJ€Ø€‡�Ô à€y‡~�~Ó€Ø
€Ø	€Ø Ñ	%€ñ
˜Tó ð 
�dó 
ð!�Só !ò ð ‡�ˆƒñ)ó ð)ð ‡�ˆÓñó ðð0 ‡�ˆ+Óñó ðð0 ‡�ˆ,Óñ_Dó ð_DðD ‡�ˆ+Óñ!ó ð!ð ‡�ˆÓñ	ó ð	ð ‡�ˆÓñ3ó ð3ð4 ‡�Ð	Óñ5ó ð5ð( ‡�Ð	'Ó(ñ-ó )ð-ð ‡�ˆ+Óñ7ó ð7ð ‡�ˆ,Óñ@5ó ð@5ðJ ‡�ˆÓñ<ó ð<ð( ‡�ˆ/Óñ/ó ð/ð4 ‡�Ð
Ó ñ4ó !ð4ð ‡�Ð
!Ó"ñ!ó #ð!òð ‡�Ð	Óñ/ó ð/òMð  ˆzÒÙ…Fð r2   