
    Vh]W                     z    d dl mZmZmZ eZdZdZdZd dl	m
Z
mZ d dlmZ  G d de      Zd	 Zed
k(  r e        yy)    )absolute_importdivisionprint_functiona%  
module: infinity
short_description: Manage Infinity IPAM using Rest API
description:
  - Manage Infinity IPAM using REST API.
author:
  - Meirong Liu (@MeganLiu)
extends_documentation_fragment:
  - community.general.attributes
attributes:
  check_mode:
    support: none
  diff_mode:
    support: none
options:
  server_ip:
    description:
      - Infinity server_ip with IP address.
    type: str
    required: true
  username:
    description:
      - Username to access Infinity.
      - The user must have REST API privileges.
    type: str
    required: true
  password:
    description:
      - Infinity password.
    type: str
    required: true
  action:
    description:
      - Action to perform.
    type: str
    required: true
    choices: [add_network, delete_network, get_network, get_network_id, release_ip, release_network, reserve_network, reserve_next_available_ip]
  network_id:
    description:
      - Network ID.
    type: str
  ip_address:
    description:
      - IP Address for a reservation or a release.
    type: str
  network_address:
    description:
      - Network address with CIDR format (for example V(192.168.310.0)).
    type: str
  network_size:
    description:
      - Network bitmask (for example V(255.255.255.220) or CIDR format V(/26)).
    type: str
  network_name:
    description:
      - The name of a network.
    type: str
  network_location:
    description:
      - The parent network ID for a given network.
    type: int
    default: -1
  network_type:
    description:
      - Network type defined by Infinity.
    type: str
    choices: [lan, shared_lan, supernet]
    default: lan
  network_family:
    description:
      - Network family defined by Infinity, for example V(IPv4), V(IPv6) and V(Dual stack).
    type: str
    choices: ['4', '6', dual]
    default: '4'
a  
- hosts: localhost
  connection: local
  strategy: debug
  tasks:
    - name: Reserve network into Infinity IPAM
      community.general.infinity:
        server_ip: 80.75.107.12
        username: username
        password: password
        action: reserve_network
        network_name: reserve_new_ansible_network
        network_family: 4
        network_type: lan
        network_id: 1201
        network_size: /28
      register: infinity
a  
network_id:
  description: ID for a given network.
  returned: success
  type: str
  sample: '1501'
ip_info:
  description: When reserve next available IP address from a network, the IP address info is returned.
  returned: success
  type: str
  sample: '{"address": "192.168.10.3", "hostname": "", "FQDN": "", "domainname": "", "id": 3229}'
network_info:
  description: When reserving a LAN network from a Infinity supernet by providing network_size, the information about the
    reserved network is returned.
  returned: success
  type: str
  sample: {
    "network_address": "192.168.10.32/28",
    "network_family": "4",
    "network_id": 3102,
    "network_size": null,
    "description": null,
    "network_location": "3085",
    "ranges": {"id": 0, "name": null, "first_ip": null, "type": null, "last_ip": null},
    "network_type": "lan",
    "network_name": "'reserve_new_ansible_network'"
  }
)AnsibleModulejson)open_urlc                   |    e Zd ZdZd Z	 	 	 	 	 ddZddZddZddZddZ	dd	Z
	 	 	 	 dd
Z	 	 	 ddZ	 	 	 ddZy)Infinityz<
    Class for manage REST API calls with the Infinity.
    c                 T    || _         || _        || _        dt        |      z  | _        y )Nzhttps://%s/rest/v1/)module	auth_user	auth_passstrbase_url)selfr   	server_ipusernamepasswords        n/home/dcms/DCMS/lib/python3.12/site-packages/ansible_collections/community/general/plugins/modules/infinity.py__init__zInfinity.__init__   s'    !!-Y@    Nc                    |dgn|}t        | j                        t        |      z   }d}ddi}|s| j                  j                  d       |r%t	        |t               st        j                  |      }t        t        |      |d|| j                  | j                  dd	|
	      }	|	j                         }d}
|	j                  |vr+| j                  j                  dd|	j                  z         nEt	        |t               rt        |      dkD  r|}
n$|j                         dk(  r|	j                  dk(  rd}
t	        |
t              r/d|
v r+| j                  j                  dd       t        |
d         |
S )zN
        Perform the HTTPS request by using ansible get/delete method
        N   zContent-Typezapplication/jsonzEWhen sending Rest api call , the resource URL is empty, please check.msg   FT)methodtimeoutheadersurl_usernameurl_passwordvalidate_certsforce_basic_authdata z: openurl response_raw.code show error and error code is %rchangedmetar   delete   zDelete is done.textz1when calling rest api, returned data is not json )r   r   r   	exit_json
isinstancer   dumpsr   r   r   readcodelenlowerdict	Exception)r   r   resource_url
stat_codesparamspayload_datarequest_urlresponser   response_rawpayloads              r   _get_api_call_ansible_handlerz&Infinity._get_api_call_ansible_handler   ss    )0cUj
$--(3|+<<!#56KK!![ " ]
< =::l3L !	  $$&J.KK!!Q""$ " %
 (C(S]Q->"8+0A0AS0H+gt$7):KK!!H " J GFO,,r   c                    ||| j                   j                  d       d}d}i }d}|r dt        |      z   }| j                  ||      }||rd}d}dt	        j
                  |d	d
      i}| j                  ||t	        j
                  |            }|r%t        |t              rt	        j                  |      }|r=t        |t              r-t        |      dkD  r|dk(  r|d   }t	        j
                  |      }|S )z
        Search network_name inside Infinity by using rest api
        Network id  or network_name needs to be provided
        return the details of a given with given network_id or name
        NzDYou must specify  one of the options 'network_name' or 'network_id'.r   getr%   	networks/searchquerynetworknametyper8      r   )
r   r,   r   r=   r   r.   r-   loadslistr1   )r   
network_idnetwork_namelimitr   r5   r7   r:   s           r   get_networkzInfinity.get_network   s    J$6KK!!Z " \&Z8L99&,OH,F#Ltzz%y9 ; <F994::f3E : GHJx5::h/Jx63< !<"&+qj#A;::h/r   c                 Z   d}d}d}|| j                   j                  d       dt        j                  |dd      i}| j	                  ||t        j                  |      	      }d
}|r%t        |t              rt        j                  |      }|rt        |t              r
|d   }|d   }|S )zZ
        query network_id from Infinity  via rest api based on given network_name
        r?   rA   Nz*You must specify the option 'network_name'r   rB   rC   rD   rG   r%   r   id)	r   r,   r   r.   r=   r-   r   rI   rJ   )r   rL   network_typer   r5   r:   r7   rK   s           r   get_network_idzInfinity.get_network_id   s     KK!!@ " B4::!957 855Ltzz&/A 6 C

8S1zz(+H
8T2{H!$Jr   c                 D   d}d}d}d}|s| j                   j                  d       |rwdt        |      z   dz   }| j                  ||      }|rR|j	                  d      d	k\  r>|j	                  d
      d	k\  r*|j	                  d      }|j	                  d      }|||dz    }|S )z
        Reserve ip address via  Infinity by using rest api
        network_id:  the id of the network that users would like to reserve network from
        return the next available ip address from that given network
        postr%   Nz)You must specify the option 'network_id'.r   r@   z/reserve_ip[r   ]{}rH   )r   r,   r   r=   find)r   rK   r   r5   r:   ip_info	start_posend_poss           r   reserve_next_available_ipz"Infinity.reserve_next_available_ip  s     KK!!? " A&Z8=HL99&,OHHMM"*--"4"9$MM#.	"--,"9w{<r   c                    d}d}d}||| j                   j                  d       dt        |      z   dz   }| j                  ||      }|s#| j                   j                  d|d	|d
       t	        j
                  |      }g }|D ]  }|d   }	|j                  |	        d}
|D ]R  }	d}dt        |	      z   }| j                  ||dg      }|s+t	        j
                  |      d   t        |      k(  sP|	}
 n |
r'd}dt        |
      z   }| j                  ||dg      }|S | j                   j                  d|d|d       |S )zD
        Reserve ip address via  Infinity by using rest api
        r?   r%   NzCYou must specify  those two options: 'network_id' and 'ip_address'.r   r@   	/childrenz There is an error in release ip z from network  .rP   zip_addresses/r   r6   addressr)   r*   z0 When release ip, could not find the ip address z from the given network z' .)r   r,   r   r=   r   rI   append)r   rK   
ip_addressr   r5   r:   ip_list	ip_idlistip_itemip_iddeleted_ip_idip_responses               r   
release_ipzInfinity.release_ip   s    !3KK!!Y " [ #S_4{B55flKKK!!Z) " * **X&	 	$GDMEU#	$  
	EK*SZ7L<<5 = "K tzz !!* ,/2: ? %
	 F*S-??L99# : 8H 	 KK!!Z) " * r   c                     d}d}d}||| j                   j                  d       ||r| j                  |      }|r#dt        |      z   }| j	                  ||dg	      }|S )
zA
        delete network from  Infinity by using rest api
        r)   r%   NzDYou must specify one of those options: 'network_id','network_name' .r   )rL   r@   r*   ra   )r   r,   rR   r   r=   )r   rK   rL   r   r5   r:   s         r   delete_networkzInfinity.delete_networkR  s     ,"6KK!!Z " \,,,,,GJ&Z8L99# : 8Hr   c                    d}d}	d}
|||| j                   j                  d       |rdt        |      z   dz   }	|sd}|sd	}|||||t        |      d
}|r|j	                  d|i       | j                  ||	ddg|      }
|
S )a  
        Reserves the first available network of specified size from a given supernet
         <dt>network_name (required)</dt><dd>Name of the network</dd>
            <dt>description (optional)</dt><dd>Free description</dd>
            <dt>network_family (required)</dt><dd>Address family of the network. One of '4', '6', 'IPv4', 'IPv6', 'dual'</dd>
            <dt>network_address (optional)</dt><dd>Address of the new network. If not given, the first network available will be created.</dd>
            <dt>network_size (required)</dt><dd>Size of the new network in /&lt;prefix&gt; notation.</dd>
            <dt>network_type (required)</dt><dd>Type of network. One of 'supernet', 'lan', 'shared_lan'</dd>

        rT   r%   NzaYou must specify those options: 'network_id', 'reserved_network_name' and 'reserved_network_size'r   r@   z/reserve_network4lan)rL   descriptionnetwork_sizenetwork_familyrQ   network_locationnetwork_addressr      )r6   r8   )r   r,   r   intupdater=   )r   rK   reserved_network_namereserved_network_descriptionreserved_network_sizereserved_network_familyreserved_network_typereserved_network_addressr   r5   network_infor8   s               r   reserve_networkzInfinity.reserve_networkf  s     !6!>BWB_KK!!w " y&Z8;MML&&)#$$)!17151 #J1 $!24L MN99Lc3Zl : T r   c                    d}d}||| j                   j                  d       d}dt        |      z   dz   }| j                  ||      }|s#| j                   j                  d|d	|d
       |r7t	        j
                  |      }|D ]  }|d   s	|d   d   |k(  s|d   d   } n d}|r'd}dt        |      z   }| j                  ||dg      }|S | j                   j                  d|d|d       |S )zk
        Release the network with name 'released_network_name' from the given  supernet network_id
        r?   Nz`You must specify those options 'network_id', 'reserved_network_name' and 'reserved_network_size'r   r%   r@   r_   z( there is an error in releasing network z  from network  r`   rC   rL   rK   r)   r*   ra   z5 When release network , could not find the network   z from the given superent z' )r   r,   r   r=   r   rI   )	r   rK   released_network_namereleased_network_typer   r:   matched_network_idr5   	child_nets	            r   release_networkzInfinity.release_network  sB    !6!>KK!!v " x"S_4{B55flKKK!!24 " 5 zz(+H% 	Y'Ii,@,PTi,i)29)=l)K& F&-?)@@L99# : 8H 	 KK!!&
4 " 5 r   c                     d}d}d}	|||| j                   j                  d       |sd}|sd}|sd}||||||d	}
| j                  d|d
g|
      }	|	S )z
        add a new LAN network into a given supernet Fusionlayer Infinity via rest api  or default supernet
        required fields=['network_name', 'network_family', 'network_type',  'network_address','network_size' ]
        rT   networksNzTYou must specify  those options 'network_name', 'network_address' and 'network_size'r   ro   rp   )rL   ru   rr   rs   rQ   rt   r   )r   r5   r6   r8   )r   r,   r=   )r   rL   ru   rr   rs   rQ   rt   r   r5   r:   r8   s              r   add_networkzInfinity.add_network  s     !?#:l>RKK!!j " l  N L!(.(,( 02 55u< 6 9 r   )r?   r%   NNN)r   )r%   rp   )r%   )r%   r%   )r%   r%   r%   r%   ro   rp   r%   )r%   r%   rp   )r%   r%   r%   ro   rp   r   )__name__
__module____qualname____doc__r   r=   rN   rR   r]   rk   rm   r   r   r    r   r   r
   r
      st    A /hD24-d( *,OQJMNP'\ "$"'	%V 46,/13r   r
   c                     t        t        t        dd      t        dd      t        ddd      t        d      t        d      t        d      t        dd      t        dd	g d
      t        ddg d      t        d      t        d      t        ddg d            ddgf      } | j                  d   }| j                  d   }| j                  d   }| j                  d   }| j                  d   }| j                  d   }| j                  d   }| j                  d   }| j                  d   }	| j                  d   }
| j                  d   }| j                  d   }t        | |||      }d}|dk(  r?|r<|j	                  |      }|sd }| j                  d!|"       | j                  d|"       y y |d#k(  r-|r*|r'|j                  ||$      }| j                  d|"       y y y |d%k(  r'|j                  ||&      }| j                  d|"       y |d'k(  r'|j                  ||	(      }| j                  d|"       y |d)k(  r'|j                  ||&      }| j                  d|"       y |d*k(  r+|j                  |||||	|
+      }| j                  d|"       y |d,k(  r(|j                  |||	-      }| j                  d|"       y |d.k(  r+|j                  |||
|||	/      }| j                  d|"       y y )0Nr   T)rF   required)rF   r   no_log)rF   rw   r   )rF   defaultro   )ro   6dual)rF   r   choicesrp   )rp   
shared_lansupernet)r   rm   rN   rR   rk   r   r   r]   )rF   r   r   )r   r   r   rK   rd   rL   rt   rs   rQ   ru   rr   actionr   r   )argument_specrequired_togetherr   r   rK   rd   rL   rs   rQ   ru   rr   rt   r%   r]   z@There is an error in calling method of reserve_next_available_ipFr&   rk   )rK   rd   rm   )rK   rL   rR   )rL   rQ   rN   r   )rK   ry   r{   r|   r}   r~   r   )rK   r   r   r   )rL   rt   ru   rr   rs   rQ   )r   r3   r7   r
   r]   r,   rk   rm   rR   rN   r   r   r   )r   r   r   r   r   rK   released_iprL   rs   rQ   ru   rr   rt   my_infinityresults                  r   mainr     sc   5ut4utDA''5)!ub9UCAST5%Abc e,5)UT 	< 	
0 $
1F8 k*I}}Z(H}}Z(H]]8$F|,J---K==0L]]#34N==0Lmm$56O==0L}}%7869hAKF,, :::FF[  V <T7  
<	+ ++%+ , ?FT7 &: 
#	#++! , >F3	#	#++%L , BF3	=	 ((! ) >F3	$	$,,!".".$2".%4 - 6 	F3	$	$,,!".". - 0 	F3	=	 ((%-+%)% ) ' 	F3 
!r   __main__N)
__future__r   r   r   rF   __metaclass__DOCUMENTATIONEXAMPLESRETURNansible.module_utils.basicr   r   ansible.module_utils.urlsr   objectr
   r   r   r   r   r   <module>r      s\    C BJX&
< ; .Ov Od
]4@ zF r   