
    Mf:                     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	Z	d dl
Z
d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ d d	lmZ 	 d dlmZ d dlZn# e$ r dZY nw xY w eed
d          Z  eedd          Z! e"d e#             e$                      Z% e&e          D ]MZ'e'(                    d          s6e')                                r" e*e%e' eee' eee'                               Nd Z+ G d d          Z, G d dej-                  Z. G d de.          Z/dS )    N)	b64encode)BytesIO)models)MatplotlibFigure)checks)ImproperlyConfigured)settings)conf
MEDIA_ROOT 	MEDIA_URLr	   _c                 R    	 t          j        |            d S # t          $ r Y d S w xY wN)osremoveIOError)paths    W/var/www/surfInsights/venv3-11/lib/python3.11/site-packages/django_matplotlib/fields.pycleanup_filer   %   s:    
	$   s    
&&c                       e Zd ZdZ	 	 ddZed             Zed             Zed	             Z	e	j
        d
             Z	ed             Zej
        d             ZdS )FigureObject)typesourcer   errorformat_width_height@     stringr   c                 h    || _         || _        || _        || _        || _        d| _        d| _        d S )Nr   )r   r   r   r   r   r   r   )selfwidthheightr   r   r   s         r   __init__zFigureObject.__init__0   s7    		
    c                     | j         rt          sdS | j                             t          d          }t          j                             dt          |          S )Nr   /)r   r   replacer   r   join)r#   r   s     r   urlzFigureObject.url:   sG    y 		 	2y  R00w||CD111r'   c                 &   t          | t                    rt          |           dz   S t          | t                    rT|                                                     d          r|                                 S |                                 r| dz   S d S )Npx)
isinstanceintstrlowerendswith	isnumeric)ss    r   _prepare_sizezFigureObject._prepare_sizeA   s    a 	 q66D= 3 	 wwyy!!$''  wwyy   4xtr'   c                 6    |                      | j                  S r   )r6   r   r#   s    r   r$   zFigureObject.widthL   s    !!$+...r'   c                     || _         d S r   )r   r#   values     r   r$   zFigureObject.widthP   s    r'   c                 6    |                      | j                  S r   )r6   r   r8   s    r   r%   zFigureObject.heightT   s    !!$,///r'   c                     || _         d S r   )r   r:   s     r   r%   zFigureObject.heightX   s    r'   N)r   r    r!   r   r   )__name__
__module____qualname__	__slots__r&   propertyr,   staticmethodr6   r$   setterr%    r'   r   r   r   ,   s        0I *-02    2 2 X2   \ / / X/ \  \ 0 0 X0 ]  ]  r'   r   c                   (     e Zd Z fdZ fdZ xZS )MatplotlibFieldBasec                      t                      j        ||fi | d| _        |j                            | d           t          |||            d S )NFT)private)supercontribute_to_classconcrete_meta	add_fieldsetattr)r#   clsnamekwargs	__class__s       r   rK   z'MatplotlibFieldBase.contribute_to_class^   s^    ##C88888	D$///T4     r'   c                     t                                                      \  }}}}||t                      t                      fS r   )rJ   deconstructtupledict)r#   rQ   r   argsrR   rS   s        r   rU   zMatplotlibFieldBase.deconstructd   s:    #(77#6#6#8#8 dD& T577DFF**r'   )r>   r?   r@   rK   rU   __classcell__rS   s   @r   rG   rG   ]   sQ        ! ! ! ! !+ + + + + + + + +r'   rG   c                   ~     e Zd ZdZ fdZd Zed             Zd Zd Z	d Z
dd	Z fd
Zd Zd Zd Z fdZ xZS )MatplotlibFigureFielda  Matplotlib figure field for Django.

    Figures are generated in 'png' (default) or 'svg' formats.
    They can be inserted to html documents as inline objects 
    (e.g. using `<img src="data:image/png;base64,...">`) or saved to 
    temporary files.

    If files are saved on disk, they are automatically cleaned up when the
    program exits using :mod:`atexit` module.

    `MatplotlibFigureField` is compatible with standard Django Admin app. 

    Figures automatically re-render (at any subsequent request) 
    when they code is changed. It uses :func:`hashlib.md5` function to
    check changes in figure's code. If the figure wasn't changed, 
    it would be stored in memory and underlying figure view function (which returns 
    :class:`matplotlib.Figure` instance) not be called for each subsequent
    request.
    
    .. note::

       Model fields created using this class aren't stored in the database 
       and no additional columns for such fields are created.

    c                 d   t           j        }|                    dd          | _        |                    d|                    d                    | _        |                    dt                                | _        |                    dt                                | _	        |                    d|                    d                    | _
        |                    d|                    d                    | _        |                    d|                    d                    | _        |                    d	|                    d	                    | _        |                    d
|                    d
                    | _        d| _        d|d<    t!                      j        |i | dS )a  MatplotlibFigureField initializer.

        This field can take any of standard Django's field attributes,
        but forces `required` argument to `False` for corresponding form.

        :param figure: The name of callable within `figures.py` which should 
                       return matplotlib.Figure object.
        :type figure: str
        :param silent: Be silent on exceptions or not (default is `False`). 
        :type figure: bool
        :param plt_args: Positional arguments passed to figure's view 
                         (the function defined by the `figure` parameter).
        :type plt_args: tuple
        :param plt_kwargs: Keyword arguments passed to figure's view 
                           (the function defined by the `figure` parameter).        
        :type plt_kwargs: dict
        :param fig_width: Output figure width in pixels. Default is 320.
        :type fig_width: int
        :param fig_height: Output figure height in pixels. Default is 240.
        :type fig_height: int
        :param output_type: Output type of the figure. Either 'file' or
                            'string'. Default is 'string' (used for inline
                            figure object embedding to html pages).
        :type output_type: str
        :param output_format: Output format of the figure. Either 'svg' or
                              'png' (default).
        :type output_format: str
        :param cleanup: Defines whether created files be cleaned up at program
                        exit or not. Default is True (created files will be
                        erased at exit). Has sense only if `output_type='file'`.
        :type cleanup: bool


        .. note::

            Default parameters for MatplotlibFigureField are defined in the file
            conf.py.


        .. note:: 

            If `output_type='file'`,  MEDIA_ROOT should be defined in your
            project settings file. In this case, the field will 
            save temporary files to the folder `MEDIA_ROOT/DJANGO_MATPLOTLIB_TMP`.
            Default value of `DJANGO_MATPLOTLIB_TMP` is defined in `conf.py` and
            can be overridden in your project settings file.

        figurer   silentplt_args
plt_kwargs	fig_width
fig_heightoutput_typeoutput_formatcleanupNTnull)defaultsDJANGO_MATPLOTLIB_FIG_DEFAULTSpopr^   getr_   rV   r`   rW   ra   rb   rc   rd   re   fig_cleanup_figure_modulerJ   r&   )r#   rX   rR   defsrS   s       r   r&   zMatplotlibFigureField.__init__   sX   d 6jj2..jj488H+=+=>>

:uww77 **\466::K+1F1FGG **\488L3I3IJJ!::mTXXm5L5LMM#ZZ(,(A(AC C!::i)1D1DEE"v$*6*****r'   c                    d }t          j        |          }| j        r0|d                    t	          t
          | j                            z  }| j        r9|d                    d | j                                        D                       z  }|r9t          j	        |
                    d                                                    }|S )Nr   c                 R    g | ]$\  }}t          |          t          |          z   %S rE   )r1   ).0kvs      r   
<listcomp>z:MatplotlibFigureField._get_figure_hash.<locals>.<listcomp>   s,    SSS41as1vvASSSr'   utf-8)inspect	getsourcer`   r+   mapr1   ra   itemshashlibmd5encode	hexdigest)r#   funcnew_hashr   s       r   _get_figure_hashz&MatplotlibFigureField._get_figure_hash   s    "4((= 	7bggc#t}55666F? 	UbggSS4?;P;P;R;RSSSTTTF 	G{6==#9#9::DDFFHr'   c                 p   t           j                            t          t          j                  }t          j        |d           d                    d t          d          D                       }|d| j        z   z  }t           j                            ||          }t           j        	                    |          rxd                    d t          d          D                       }|d| j        z   z  }t           j                            ||          }t           j        	                    |          x|S )NT)exist_okr   c                 J    g | ] }t          j        t          j                  !S rE   randomchoicer!   ascii_lowercaserq   r   s     r   rt   z:MatplotlibFigureField.suggest_filename.<locals>.<listcomp>   s%     Z Z Z1v/E!F!F Z Z Zr'   
   .c                 J    g | ] }t          j        t          j                  !S rE   r   r   s     r   rt   z:MatplotlibFigureField.suggest_filename.<locals>.<listcomp>   s%    $^$^$^qV]63I%J%J$^$^$^r'   )
r   r   r+   r   rh   DJANGO_MATPLOTLIB_TMPmakedirsrangere   exists)r#   tmp_dirsuggest_fname	file_paths       r   suggest_filenamez&MatplotlibFigureField.suggest_filename   s   ',,z8+IJJ
Gd++++ Z ZPUVXPYPY Z Z Z[[t111GLL-88	gnnY'' 	=GG$^$^TYZ\T]T]$^$^$^__MS4#555MWm<<I gnnY'' 	= r'   c                 n    |                      |          }t          | d          sdS || j        k    rdS dS )N	_fig_hashTF)r   hasattrr   )r#   r~   r   s      r   _is_figure_changedz(MatplotlibFigureField._is_figure_changed   sC    ((..t[)) 	4t~%%45r'   c                    t           rt          j        d           |                     |          r|                     |          \  }}t          |          rft                      }	  || j        i | j        }t          |t           j
                  s,d| j        z  |_        | j        r|S t          |j                  n)# t          $ r}||_        | j        r|cY d }~S |d }~ww xY w| j        |_        | j        |_        | j        |_        | j        |_        | j        dk    rt0          s| j        r
d|_        	 |S t0          st3          d          | j        |_        d|_        |                    |j        | j        d           | j        rt?          j         tB          |j                   n| j        d	k    rtE                      }|                    || j        d           |#                    d
           d|_        | j        dk    r:tI          |%                                          &                    d          |_        n,|%                                &                    d          |_        t          j'        |           nd|_        	 |j        s|j        r| (                    |          | _)        || _*        n|| _*        d| _)        |S | j*        S )NAggz4%s should return instance of class Matplotlib.FigurefilezMEDIA_ROOT isn't configured. zDYou need to set up MEDIA_ROOT variable in your project sttings file.r   tight)r   bbox_inchesr!   r   pngru   zUndefined figure type. )+plt
matplotlibuser   _reload_func_sourcecallabler   r`   ra   r/   Figurer^   r   r_   	TypeError	Exceptionrb   r$   rc   r%   rd   r   re   r   r   r   r   r   r   savefigrl   atexitregisterr   r   seekb64enreaddecodecloser   r   _figure_object)r#   r~   
fig_objectfigebuffers         r   _get_figurez!MatplotlibFigureField._get_figure   s    	"N5!!!""4(( <	"#77==J~~ :")^^
>$AAAC &c3:66 >,=?C{,K
(; >#--"+J,<"="==> !      '(J${  )))))))  $(>
 $(O
!"&"2
$($6
!#v--% G$+ G+J
(;))' G2 4F G G G&*&;JO(*J%KK
8J,3   5 5 5' GjoFFF%11$YYFKKt/A,3   5 5 5KKNNN&(JO)U22,1&++--,@,@,G,G,P,P
))+1;;==+?+?+H+H
)IcNNNN'@J$?? Aj&7 A%)%:%:4%@%@DN&0## '1#!#!!""s$   )C 
C(C#C(!C##C(c                 N   t                      }d}	 t          j                            t	          j        |                    }t          j                            t          j
                            d          d         t          j                            |t          j
                            }t          j                            |          | _        |j                            | j                   nC# t"          $ r6 dt          j
        z  |_        | j        r||fcY S t#          |j                  w xY wt)          | j        | j                  s<d| j        dt          j
        d|_        | j        r||fS t-          |j                  |t/          | j        | j                  fS )z Returns reloaded function Nr   r   z*Couldn't locate '%s' in the app directory.zCouldn't locate callable 'z' within module 'z'.)r   r   r   dirnamerv   getsourcefile	importlibutilspec_from_file_locationrh   DJANGO_MATPLOTLIB_MODULEsplitr+   module_from_specrm   loaderexec_moduleImportErrorr   r_   r   r^   AttributeErrorgetattr)r#   ownerr   r~   current_dirspecs         r   r   z)MatplotlibFigureField._reload_func_source+  s    "^^
	4'//'*?*F*FGGK>99177<<Q?[ ( AC C D
 #,."A"A$"G"GDK##D$78888 	4 	4 	4  ( A BJ{ 4"D))))!*"2333	4 t*DK88 	7 	7&*kkk111 J { 7"D))$Z%566674#6DDDDs   CC2 2)D2D2Nc                     |rQ|                      |          \  }}t          |          r!|                     |          | _        | j        S || _        |S d S r   )r   r   r   r   )r#   attrr   fig_objr~   s        r   __get__zMatplotlibFigureField.__get__L  se     	 44U;;MGT~~ &*&6&6t&<&<#**&-#	 	r'   c                     g  t                      j        di | | j        di | | j        di | | j        di |S )NrE   )rJ   check_check_figure_attribute_check_fig_format_check_fig_type)r#   rR   rS   s     r   r   zMatplotlibFigureField.checkV  s    
UWW]$$V$$
)T)33F33
 $T#--f--
 "T!++F++	
 	
r'   c                 H    | j         dvrt          j        d| d          gS g S )N)svgr   z7Attribute 'fig_format' should be either 'png' or 'svg'.zdjango_matplotlib.E003objid)re   r   Errorr#   rR   s     r   r   z'MatplotlibFigureField._check_fig_format^  s>    ^33M/    	r'   c                 H    | j         dvrt          j        d| d          gS g S )N)r!   r   z9Attribute 'fig_type' should be either 'string' or 'file'.zdjango_matplotlib.E004r   )rd   r   r   r   s     r   r   z%MatplotlibFigureField._check_fig_typei  s?    #555O/    	r'   c                     | j         st          j        d| d          gS t          | j         t                    st          j        d| d          gS g S )Nz?MatplotlibFigrueField must define non-empty 'figure' attribute.zdjango_matplotlib.E002r   z$'figure' must be a non-empty string.zdjango_matplotlib.E001)r^   r   r   r/   r1   r   s     r   r   z-MatplotlibFigureField._check_figure_attributet  sy    { 	4/	    DK-- 		:/    Ir'   c                     |                      d| j                   t          t          | j        d}|                    |            t                      j        di |S )Nr   )r   )
form_classchoices_form_classinitialrE   )r   modelr   r   updaterJ   	formfield)r#   rR   rh   rS   s      r   r   zMatplotlibFigureField.formfield  sd    Rtz***"2*:#24 4 	 uww ,,8,,,r'   r   )r>   r?   r@   __doc__r&   r   rB   r   r   r   r   r   r   r   r   r   r   rY   rZ   s   @r   r\   r\   k   s        4?+ ?+ ?+ ?+ ?+B	 	 	 
 
 X
  A# A# A#FE E EB   
 
 
 
 
	 	 		 	 	  *- - - - - - - - -r'   r\   )0r   rer   rv   r!   r   base64r   r   rz   r   ior   	django.dbr   django_matplotlib.formsr   django.corer   django.core.exceptionsr   django.confr	   django_matplotlibr
   
djmpl_confmatplotlib.pyplotpyplotr   r   r   r   r   r   r   rV   rW   rh   dirrQ   
startswithisupperrO   r   r   FieldrG   r\   rE   r'   r   <module>r      s   				 				        % % % % % %               4 4 4 4 4 4       7 7 7 7 7 7             0 0 0 0 0 0######   
CCC WX|R00
GHk2..	 4
EEGGTTVV,,C
OO D DD??3 DDLLNN D$$
D(A(ABB	D 	D 	D
  . . . . . . . .b+ + + + +&, + + +d- d- d- d- d-/ d- d- d- d- d-s   
A A'&A'