o
    Df!                     @   s  d 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 ddl	m
Z
mZ ddlmZ ddlmZ dd	lmZ dd
lmZmZ dedee fddZdeee
f dee fddZdeee
f dedededef
ddZ			d/deee
f dee dee dee def
ddZdedefddZdeee
f defd d!Zd"d# Z	d0d%d&Z d1deee
f fd'd(Z!					)	*	$	d2dee dee dee dee deded+ed,ee de"fd-d.Z#dS )3z
Based on the logic in the PROJ projsync CLI program

https://github.com/OSGeo/PROJ/blob/9ff543c4ffd86152bc58d0a0164b2ce9ebbb8bec/src/apps/projsync.cpp
    N)datetime)partial)Path)AnyOptional)urlretrieve)get_proj_endpoint)BBox)get_data_dirget_user_data_dircoordsreturnc                 C   s   zt |  \}}tt|t|t|t|dW S  ty    Y nw d}| D ]-}t|}|du r2|}q%t|j|j|_t|j|j|_t|j|j|_t|j	|j	|_	q%|S )z/
    Get the bounding box from coordinates
    )westsoutheastnorthN)
zipr	   minmax
ValueError_bbox_from_coordsr   r   r   r   )r   xxxyyy
coord_bbox	coord_setbbox r   D/home/ubuntu/webapp/venv/lib/python3.10/site-packages/pyproj/sync.pyr      s    "r   geomc                 C   s  d| vsd| vr
dS | d }| d dkrt |S d}d}g }|D ]}t |}|du r+q |jdkr3d}n|jdkr:d}|| q d}|D ]<}|rY|rY|jdkrYd|_| jd	7  _|du r`|}qDt|j|j|_t|j|j|_t|j|j|_t|j|j|_qD|S )
z4
    Get the bounding box from geojson geometry
    coordinatestypeNMultiPolygonFLT   h  )r   r   r   appendr   r   r   r   )r   r   found_minus_180found_plus_180bboxescoordinate_setr   	grid_bboxr   r   r   _bbox_from_geom*   s:   

r+   featurer   spatial_testinclude_world_coveragec                 C   s   |  d}|durRt|}|du rdS |j|j dkr3|j|j dkr3|s'dS td |_td|_n|jdkrK|jdk rK| jd	8  _| jd	8  _t|||S dS )
zC
    Filter by the bounding box. Designed to use with 'filter'
    geometryNFig     infr#   r"   r$   )getr+   r   r   r   r   floatgetattr)r,   r   r-   r.   r   	geom_bboxr   r   r   _filter_bboxN   s    
r6   	source_idarea_of_usefilenamec           
      C   s~   |  d}|s	dS | d}| d}|r|sdS |du p ||v }|du p,|| ddv }|du p4||v }	|r=|r=|	r=dS dS )	zA
    Filter by the properties. Designed to use with 'filter'
    
propertiesFnamer7   Nr8    T)r2   )
r,   r7   r8   r9   r:   
p_filenamep_source_idsource_id__matchedarea_of_use__matchedfilename__matchedr   r   r   _filter_propertiesh   s   
	

rB   	grid_namec                 C   s@   t t |  r
dS t tjD ]}t ||  r dS qdS )zX
    Run through all of the PROJ directories to see if the
    file already exists.
    FT)r   r   existsr
   splitospathsep)rC   data_dirr   r   r   _is_download_needed   s   rI   c                 C   s,   |  d}|s	dS | d}|sdS t|S )zM
    Filter grids so only those that need to be downloaded are included.
    r:   Fr;   )r2   rI   )r,   r:   r9   r   r   r   _filter_download_needed   s   

rJ   c                    sb   t  }t| d t fdddD ]}|| qW d   | S 1 s(w   Y  | S )z7
    Return sha256 checksum of file given by path.
    rbc                      s
     dS )Ni   )readr   filer   r   <lambda>   s   
 z_sha256sum.<locals>.<lambda>    N)hashlibsha256openiterupdate	hexdigest)
input_filehasherchunkr   rM   r   
_sha256sum   s   
rZ   Fc                 C   s   |r	t d|   t|| d}z2t| | |dur(|t|kr(td| |t|| W zt| W dS  tyC   Y dS w zt| W w  tyT   Y w w )z.
    Download resource file from PROJ url
    zDownloading: z.partNzSHA256 mismatch: )	printr   r   rZ   RuntimeErrorreplacerF   removeFileNotFoundError)file_url
short_name	directoryverboserR   tmp_pathr   r   r   _download_resource_file   s$   
re   c                 C   sh   | du rt d} t| d}| r t t| j jdkr+t	t
  dd| d t|jddS )	zR
    Returns
    -------
    dict[str, Any]:
        The PROJ grid data list.
    NTzfiles.geojsonr   z/files.geojson)r`   ra   rb   zutf-8)encoding)r   r   rD   r   utcnowfromtimestampstatst_mtimedaysre   r   jsonloads	read_text)target_directory
local_pathr   r   r   _load_grid_geojson   s   

rq   
intersectsTinclude_already_downloadedro   c           	      C   s   t |dd }|dure|jdkr%|j|jkr%| jd8  _| jd8  _n5|jdk r?|j|jkr?| jd7  _| jd7  _nt|jdk rZt|jdk rZ|j|jk rZ| jd7  _ttt|||d|}ttt| ||d|}|rvt|S ttt	|S )	aI  
    Get a list of transform grids that can be downloaded.

    Parameters
    ----------
    source_id: str, optional
    area_of_use: str, optional
    filename: str, optional
    bbox: BBox, optional
    spatial_test: str, default="intersects"
        Can be "contains" or "intersects".
    include_world_coverage: bool, default=True
        If True, it will include grids with a global extent.
    include_already_downloaded: bool, default=False
        If True, it will list grids regardless of if they are downloaded.
    target_directory: Union[str, Path, None], optional
        The directory to download the geojson file to.
        Default is the user writable directory.

    Returns
    -------
    list[dict[str, Any]]:
        A list of geojson data of containing information about features
        that can be downloaded.
    )ro   featuresNr#   r$   r"   )r   r-   r.   )r7   r8   r9   )
rq   r   r   absfilterr   r6   rB   tuplerJ   )	r7   r8   r9   r   r-   r.   rs   ro   rt   r   r   r   get_transform_grid_list   s>   #(
	rx   )NNN)FN)N)NNNNrr   TFN)$__doc__rQ   rl   rF   r   	functoolsr   pathlibr   typingr   r   urllib.requestr   pyproj._syncr   
pyproj.aoir	   pyproj.datadirr
   r   listr   dictstrr+   boolr6   rB   rI   rJ   rZ   re   rq   rw   rx   r   r   r   r   <module>   s    $




	