Ë
    1Jj  ã                   ó`  — d Z ddlZddlZddlZddlmZ ddlZddlmZ  ej                  e
«      Zdej                  fd„Zdefd„Zdedefd	„Zded
ededz  fd„Zdedefd„Zddœdededefd„Zdededefd„Zdedefd„Zdedefd„Zdddœdededededef
d„Zdddœdededededef
d„Zy) z+Shared Anthropic helpers for blog services.é    N)ÚAny)ÚsettingsÚreturnc                  ój   — t        t        dd«      } | st        d«      ‚t        j                  | ¬«      S )NÚANTHROPIC_API_KEYÚ z ANTHROPIC_API_KEY not configured)Úapi_key)Úgetattrr   ÚRuntimeErrorÚ	anthropicÚ	Anthropic)Úkeys    úD/var/www/html/shopify_to_digistore/blogs/services/anthropic_utils.pyÚget_anthropic_clientr      s1   € Ü
”(Ð/°Ó
4€CÙÜÐ=Ó>Ð>Ü×Ñ sÔ+Ð+ó    c                  ó$   — t        t        dd«      S )NÚANTHROPIC_MODELzclaude-sonnet-4-20250514)r
   r   © r   r   Ú	get_modelr      s   € Ü”8Ð.Ð0JÓKÐKr   Útextc                 óÀ   — | j                  «       } | j                  d«      r.t        j                  dd| «      } t        j                  dd| «      } | j                  «       S )Nz```z^```(?:json)?\s*r   z\s*```$)ÚstripÚ
startswithÚreÚsub©r   s    r   Ú_strip_fencesr      sJ   € Ø�:‰:‹<€DØ‡��uÔÜ�v‰vÐ)¨2¨tÓ4ˆÜ�v‰v�j " dÓ+ˆØ�:‰:‹<Ðr   Úopenerc                 ó  — |dk(  rdnd}| j                  |«      }|dk  ryd}d}d}t        |t        | «      «      D ]G  }| |   }|rd}Œ|dk(  r|rd}Œ|d	k(  r| }Œ |rŒ#||k(  r|d
z  }Œ.||k(  sŒ4|d
z  }|dk(  sŒ?| ||d
z    c S  y)z8Return substring of first balanced JSON array or object.Ú[Ú]Ú}r   NFÚ\TÚ"é   )ÚfindÚrangeÚlen)	r   r   ÚcloserÚstartÚdepthÚ	in_stringÚescapeÚiÚchs	            r   Ú_extract_balanced_jsonr0   !   sÄ   € à˜c’M‰S s€FØ�I‰I�fÓ€EØˆq‚yØØ€EØ€IØ€FÜ�5œ#˜d›)Ö$ˆØ�!‰WˆÙØˆFØØ�Š:™)ØˆFØØ�Š9Ø%˜ˆIØÙØØ�Š<Ø�Q‰J‰EØ�6‹\Ø�Q‰JˆEØ˜‹zØ˜E A¨¡EÐ*Ò*ð% %ð& r   c                 ó¼   — | j                  dd«      j                  dd«      } | j                  dd«      j                  dd«      } t        j                  dd| «      } | S )	z Light cleanup before json.loads.u   â€œr$   u   â€�u   â€˜Ú'u   â€™z,\s*([\]}])z\1)Úreplacer   r   r   s    r   Ú_normalize_json_textr4   @   sS   € à�<‰<˜ #Ó&×.Ñ.¨x¸Ó=€DØ�<‰<˜ #Ó&×.Ñ.¨x¸Ó=€DÜ�6‰6�. %¨Ó.€DØ€Kr   T©Úexpect_arrayr6   c                ó²  — t        | «      }|g}|rt        |d«      }|r|j                  |«       t        |d«      }|r|j                  |«       d}t        «       }|D ]<  }|r||v rŒ
|j	                  |«       t        |«      }		 t        j                  |	«      c S  |r|‚t        j                  d| d«      ‚# t        j                  $ r}
|
}Y d}
~
Œtd}
~
ww xY w)zRParse Claude JSON with extraction and cleanup; raises JSONDecodeError if hopeless.r    Ú{NzNo JSON found in model responser   )	r   r0   ÚappendÚsetÚaddr4   ÚjsonÚloadsÚJSONDecodeError)r   r6   ÚrawÚ
candidatesÚblockÚ	block_objÚlast_errÚseenÚ	candidateÚ
normalizedÚexcs              r   Úloads_json_lenientrH   H   sÝ   € ä
˜Ó
€CØ ˜E€JÙÜ& s¨CÓ0ˆÙØ×Ñ˜eÔ$Ü& s¨CÓ0€IÙØ×Ñ˜)Ô$à,0€HÜ“U€DÛˆ	Ù˜I¨Ñ-ØØ�‰�ÔÜ)¨)Ó4ˆ
ð	Ü—:‘:˜jÓ)Ò)ð  ñ ØˆÜ
×
Ñ
Ð@À$ÈÓ
JÐJøô ×#Ñ#ò 	ØˆHÜûð	ús   ÂB7Â7CÃ
CÃCÚraw_textc          
      óÆ   — |rdnd}t        «       }|j                  j                  t        «       dd|› d|› d�dd| d d	 › �d
œgd¬«      }|j                  d   j
                  S )Nz
JSON arrayzJSON objecti@  zYou fix invalid z. Return ONLY valid zB, no markdown, no commentary. Escape double quotes inside strings.ÚuserzFix this invalid JSON:

i N  ©ÚroleÚcontentg        ©ÚmodelÚ
max_tokensÚsystemÚmessagesÚtemperaturer   )r   rS   Úcreater   rN   r   )rI   r6   ÚkindÚclientÚresps        r   Ú_repair_json_via_clauderY   e   sŠ   € Ù'‰<¨]€DÜ!Ó#€FØ�?‰?×!Ñ!Ü‹kØà˜t˜fÐ$8¸¸ð ?Bð Bð
 Ø7¸ÀÀ%Ð8HÐ7IÐJñð
ð ð "ó €Dð �<‰<˜‰?×ÑÐr   c                 ób  — 	 t        | d¬«      }t        |t        «      r-dD ](  }t        |j                  |«      t        «      sŒ#||   } n t        |t        «      st        d«      ‚|S # t        j                  $ r2 t        j	                  d«       t        | d¬«      }t        |d¬«      }Y Œžw xY w)NTr5   z0JSON array parse failed, asking Claude to repair)ÚpostsÚarticlesÚitemsÚtopicsÚresultszExpected JSON array from Claude)rH   r<   r>   ÚloggerÚwarningrY   Ú
isinstanceÚdictÚgetÚlistÚ
ValueError)r   ÚdataÚrepairedr   s       r   Úparse_json_arrayri   z   s¡   € ð?Ü! $°TÔ:ˆô �$œÔÛFˆCÜ˜$Ÿ(™( 3›-¬Õ.Ø˜C‘y�Ùð Gô �dœDÔ!ÜÐ:Ó;Ð;Ø€Køô ×Ñò ?Ü�‰ÐIÔJÜ*¨4¸dÔCˆÜ! (¸Ô>Šð?ús   ‚A) Á)AB.Â-B.c                 ó  — 	 t        | d¬«      }t        |t        «      r|r|d   }t        |t        «      st        d«      ‚|S # t        j                  $ r2 t        j	                  d«       t        | d¬«      }t        |d¬«      }Y Œxw xY w)NFr5   z1JSON object parse failed, asking Claude to repairr   z Expected JSON object from Claude)
rH   r<   r>   r`   ra   rY   rb   re   rc   rf   )r   rg   rh   s      r   Úparse_json_objectrk   Œ   s„   € ð@Ü! $°UÔ;ˆô �$œÔ¡$Ø�A‰wˆÜ�dœDÔ!ÜÐ;Ó<Ð<Ø€Køô ×Ñò @Ü�‰ÐJÔKÜ*¨4¸eÔDˆÜ! (¸Ô?Šð@ús   ‚A ÁABÂBi   g      à?)rQ   rT   rR   rK   rQ   rT   c                ó¸   — t        «       }|j                  j                  t        «       || dz   d|dœg|¬«      }t	        |j
                  d   j                  «      S ©Nz0 Escape double quotes inside JSON string values.rK   rL   rO   r   )r   rS   rU   r   ri   rN   r   ©rR   rK   rQ   rT   rW   rX   s         r   Úclaude_jsonro   ›   s_   € ô "Ó#€FØ�?‰?×!Ñ!Ü‹kØØÐJÑJØ!¨dÑ3Ð4Øð "ó €Dô ˜DŸL™L¨™O×0Ñ0Ó1Ð1r   iÐ  g333333Ó?c                ó¸   — t        «       }|j                  j                  t        «       || dz   d|dœg|¬«      }t	        |j
                  d   j                  «      S rm   )r   rS   rU   r   rk   rN   r   rn   s         r   Úclaude_json_objectrq   ­   s_   € ô "Ó#€FØ�?‰?×!Ñ!Ü‹kØØÐJÑJØ!¨dÑ3Ð4Øð "ó €Dô ˜TŸ\™\¨!™_×1Ñ1Ó2Ð2r   )Ú__doc__r<   Úloggingr   Útypingr   r   Údjango.confr   Ú	getLoggerÚ__name__r`   r   r   Ústrr   r   r0   r4   ÚboolrH   rY   re   ri   rc   rk   ÚintÚfloatro   rq   r   r   r   Ú<module>r|      si  ðÙ 1ã Û Û 	Ý ã Ý  à	ˆ×	Ñ	˜8Ó	$€ð,˜i×1Ñ1ó ,ðL�3ó Lð˜ð  ó ð ð ¨cð °c¸D±jó ð>˜sð  só ð ;?ò K˜Sð K°4ð KÀ3ó Kð:  cð  ¸Dð  ÀSó  ð*˜3ð  4ó ð$˜Cð  Dó ð& Øò2Øð2à
ð2ð ð	2ð
 ð2ð 
ó2ð, Øò3Øð3à
ð3ð ð	3ð
 ð3ð 
ô3r   