
    Vh9              	       ^   d dl mZmZmZ eZ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Zd dlmZmZmZ d dlmZmZ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%  e!       Z&ddddddddddddddddddddddddgZ' G d de      Z(y# e$ rZeZY dZ[ydZ[ww xY w)    )absolute_importdivisionprint_functiona  
---
author:
    - Jesse Pretorius (@odyssey4me) <jesse@odyssey4.me>
name: libvirt_qemu
short_description: Run tasks on libvirt/qemu virtual machines
description:
    - Run commands or put/fetch files to libvirt/qemu virtual machines using the qemu agent API.
notes:
    - Currently DOES NOT work with selinux set to enforcing in the VM.
    - Requires the qemu-agent installed in the VM.
    - Requires access to the qemu-ga commands guest-exec, guest-exec-status, guest-file-close, guest-file-open, guest-file-read, guest-file-write.
extends_documentation_fragment:
    - community.libvirt.requirements
version_added: "2.10.0"
options:
  remote_addr:
    description: Virtual machine name.
    default: inventory_hostname
    vars:
      - name: ansible_host
      - name: inventory_hostname
  executable:
    description:
      - Shell to use for execution inside container.
      - Set this to 'cmd' or 'powershell' for Windows VMs.
    default: /bin/sh
    vars:
      - name: ansible_shell_type
  virt_uri:
    description: Libvirt URI to connect to to access the virtual machine.
    default: qemu:///system
    vars:
      - name: ansible_libvirt_uri
N)AnsibleErrorAnsibleConnectionFailureAnsibleFileNotFound)to_bytes	to_nativeto_text)
raise_from)ConnectionBaseBUFSIZE)_parse_clixml)Display)partial)existsT
guest-exec)enablednamezsuccess-responseguest-exec-statusguest-file-closeguest-file-openguest-file-readguest-file-writec                   b     e Zd ZdZdZdZdZ fdZ fdZd
 fd	Z	 fdZ
 fdZ fd	Z xZS )
Connectionz& Local libvirt qemu based connections zcommunity.libvirt.libvirt_qemuFc                    t         rt        t        d      t                t        t        |   ||g|i | | j                  j                  | _        t        | j                  dd      rd| _        d| _        d| _        d| _        y y )Nz<libvirt python bindings must be installed to use this plugin_IS_WINDOWSFT)z.ps1z.exe )LIBVIRT_IMPORT_ERRORr   r   superr   __init___play_contextremote_addr_hostgetattr_shellhas_native_asyncalways_pipeline_modules!module_implementation_preferencesallow_executable)selfplay_context	new_stdinargskwargs	__class__s        u/home/dcms/DCMS/lib/python3.12/site-packages/ansible_collections/community/libvirt/plugins/connection/libvirt_qemu.pyr"   zConnection.__init__\   s    [\$& 	j$(yR4R6R''33
 4;;u5$(D!+/D(5ID2$)D!	 6    c                    t         t        |           | j                  s@| j	                  d      | _        | j                  j                  dj                  | j
                        | j                         	 t        j                  | j
                        | _        | j                  j                  dj                  | j                        | j                         	 | j                  j!                  | j                        | _        t%        j&                  ddi      }t%        j(                  t+        j,                  | j"                  |dd	            }|d
   d   | _        | j                  j1                  dj                  | j.                        | j                         g }t2        D ]%  }|| j.                  vs|j5                  |d          ' t7        |      d	kD  rA| j                  j                  dj                  |      | j                         t        d      t8        j                  dj                  | j:                        | j                         d| _        yy# t        j                  $ r}t        t        |            d}~ww xY w# t        j                  $ r}t        t        |            d}~ww xY w)z4 connect to the virtual machine; nothing to do here virt_urizCONNECT TO {0}hostNzFIND DOMAIN {0}executez
guest-info   r   returnsupported_commandszGUEST CAPABILITIES: {0}r   z"REQUIRED CAPABILITIES MISSING: {0}z*Domain does not have required capabilitieszESTABLISH {0} CONNECTIONT)r!   r   _connect
_connected
get_option	_virt_uri_displayvvvformatr%   libvirtopenconnlibvirtErrorr   r
   lookupByNamedomainjsondumpsloadslibvirt_qemuqemuAgentCommandcapabilitiesvvvvvREQUIRED_CAPABILITIESappendlendisplay	transport)r,   errrequest_capresponse_capmissing_capscapr1   s         r2   r<   zConnection._connects   s.   j$(*!__Z8DNMM/66t~~FTZZX?#LL8	 MM077

C$**U?"ii44TZZ@ **i%>?K::l&C&CDKKQ\^_ab&cdL ,X 67K LDMM : A A$BSBS T[_[e[efL, 5d/// ''F45 < 1$!!"G"N"N|"\cgcmcm!n./[\\KK3::4>>JQUQ[Q[K\"DO;  '' ?.y~>>? '' ?.y~>>?s0   8$I" *J "J5J		JJ=$J88J=c                    t         t        |   |||       | j                  j	                  dj                  |      | j                         t        j                  t        |d            }t        | j                  dd      r_d}dj                  d	d
| j                  j                  | j                  j                  |g      }| j                  j                  |ddd      }d|d   d|dd dd}t!        j"                  |      }t$        j	                  dj                  |      | j                         t!        j&                  t)        j*                  | j,                  |dd            }t$        j	                  dj                  |      | j                         t/        j0                  t.        j2                        }dd|d   d   id}	t!        j"                  |	      }
t$        j	                  dj                  |
      | j                         t!        j&                  t)        j*                  | j,                  |
dd            }t$        j	                  dj                  |      | j                         |d   d   st/        j0                  t.        j2                        |z
  dz  }|dk  rd}n|dkD  rd}t/        j4                  |       t!        j&                  t)        j*                  | j,                  |
dd            }|d   d   st$        j	                  dj                  |      | j                         |d   j7                  d      rt9        j:                  |d   d         }nd}|d   j7                  d      rt9        j:                  |d   d         }nd}t        | j                  dd      r|j=                  d      rt?        |      }t$        j	                  d j                  tA        |            | j                         t$        j	                  d!j                  tA        |            | j                         |d   d"   ||fS )#z/ execute a command on the virtual machine host )in_datasudoablezEXEC {0}r6   surrogate_or_stricterrorsr   F zchcp.com65001T)as_liststrict_modepreserve_rcr   r      N)pathzcapture-outputargr8   	argumentsGA send: {0}r9   GA return: {0}r   pidr:   exitedg?g-C6*?zout-datar3   zerr-datas	   #< CLIXMLzGA stdout: {0}zGA stderr: {0}exitcode)!r!   r   exec_commandr@   rA   rB   r%   shlexsplitr
   r&   r'   join_SHELL_REDIRECT_ALLNULL
_SHELL_AND_encode_scriptrI   rJ   rS   rK   rL   rM   rH   timeclock_gettimeCLOCK_MONOTONICsleepgetbase64	b64decode
startswithr   r   )r,   cmdr[   r\   cmd_args_listrequest_execrequest_exec_jsonresult_execcommand_startrequest_statusrequest_status_jsonresult_status
sleep_timestdoutstderrr1   s                  r2   ro   zConnection.exec_command   s   j$,S'H,U+,,S1

CIc:O$PQ4;;u5 H ((J1T1TVZVaVaVlVlnqrsC !KK66sDV[in6oM $%a("&$QR(
 !JJ|4O**+<=DJJO jj!>!>t{{L]_`bc!de%,,[9

K**4+?+?@ +{8,U3
 #jj8O**+>?djjQ 

<#@#@Nacdfg#hi%,,];$**M)(3,,T-A-AB]RW^_JF"#
a
JJz" JJ|'D'DT[[Reghjk'lmM  )(3 	%,,];$**M"&&z2%%mH&=j&IJFF"&&z2%%mH&=j&IJFF 4;;u5&:K:KL:Y"6*F%,,WV_=DJJO%,,WV_=DJJOX&z2FFBBr3   c           
      N   t         t        |   ||       t        j	                  d|d|| j
                         t        t        |d            st        d|z        d|dd	d
}t        j                  |      }t        j	                  dj                  |      | j
                         t        j                  t        j                  | j                  |dd            }t        j	                  dj                  |      | j
                         t!        t        |d      d      5 }t#        t%        |j&                  t(              d      D ]  }	 d|d   t+        j,                  |      j/                         dd
}t        j                  |      }	t        j1                  dj                  |	      | j
                         t        j                  t        j                  | j                  |	dd            }
t        j1                  dj                  |
      | j
                          	 ddd       dd|d   id
}t        j                  |      }t        j	                  dj                  |      | j
                         t        j                  t        j                  | j                  |dd            }t        j	                  dj                  |      | j
                         y# t2        $ r& t5        j6                          t9        d|d|      w xY w# 1 sw Y   xY w)z& transfer a file from local to domain zPUT  TO r6   r]   r^   z!file or module does not exist: %sr   wb+rf   moderh   rj   r9   r   rk   rbr3   r   r:   )handlebuf-b64failed to transfer file  to Nr   r   )r!   r   put_filerS   rA   r%   r   r	   r   rI   rJ   rB   rK   rL   rM   rH   rD   iterr   readr   r{   	b64encodedecoderO   	Exception	traceback	print_excr   )r,   in_pathout_pathrequest_handlerequest_handle_jsonresult_handlein_filechunkrequest_writerequest_write_jsonresult_writerequest_closerequest_close_jsonresult_closer1   s                 r2   r   zConnection.put_file   s   j$((;gx8tzzJhw/DEF%3g=? ? ) 
 #jj8O**+>?djjQ

<#@#@Nacdfg#hi%,,];$**M (7+@A4H 	aGggllG<cB aa#5&3H&='-'7'7'>'E'E'G&%M *.M)B&MM/"8"89K"LSWS]S]M^#'::l.K.KDKKYkmnpq.r#sLMM"3":":<"HtzzMZa	a. *-1
 "ZZ6O**+=>TZZPzz,"?"?M_abde"fg%,,\:L! ! a'')&WV^'_``a%	a 	as%   *(LCK))L)/LLL$c           	         t         t        |   ||       t        j	                  d|d|| j
                         d|ddd}t        j                  |      }t        j	                  dj                  |      | j
                         t        j                  t        j                  | j                  |d	d
            }t        j	                  dj                  |      | j
                         d|d   t        dd}t        j                  |      }t        j	                  dj                  |      | j
                         t        t        |d      d      5 }	 t        j                  t        j                  | j                  |d	d
            }	t        j!                  dj                  |	      | j
                         |j#                  t%        j&                  |	d   d                |	d   d   st        j                  t        j                  | j                  |d	d
            }	t        j!                  dj                  |	      | j
                         |j#                  t%        j&                  |	d   d                |	d   d   sddd       dd|d   id}
t        j                  |
      }t        j	                  dj                  |      | j
                         t        j                  t        j                  | j                  |d	d
            }t        j	                  dj                  |      | j
                         y# t(        $ r& t+        j,                          t/        d|d|      w xY w# 1 sw Y   xY w)z# fetch a file from domain to local zFETCH r   r6   r   rr   rh   rj   r9   r   rk   r   r:   )r   countr]   r^   r   r   eofr   r   Nr   r   )r!   r   
fetch_filerS   rA   r%   rI   rJ   rB   rK   rL   rM   rH   r   rD   r	   rO   writer{   r|   r   r   r   r   )r,   r   r   r   r   r   request_readrequest_read_jsonout_fileresult_readr   r   r   r1   s                r2   r   zConnection.fetch_file/  s   j$*7H=:L )
 #jj8O**+>?djjQ

<#@#@Nacdfg#hi%,,];$**M )'1 
 !JJ|4O**+<=DJJO(8,ABEJ 	]h]"jj)F)Ft{{Teghjk)lm/66{C$**Uv//H0Ei0PQR%h/6"&**\-J-J4;;Xiklno-p"qKMM"3":":;"GdjjMYNN6#3#3K4I)4T#UV &h/6	] *-1
 "ZZ6O**+=>TZZPzz,"?"?M_abde"fg%,,\:L!  ]##%"RZ#[\\]	] 	]s   M:D.M/M77M::Nc                 8    t         t        |           d| _        y)z. terminate the connection; nothing to do here FN)r!   r   closer=   )r,   r1   s    r2   r   zConnection.closej  s    j$%'r3   )NT)__name__
__module____qualname____doc__rT   has_pipelininghas_ttyr"   r<   ro   r   r   r   __classcell__)r1   s   @r2   r   r   S   sB    00I NG*. #DZCx<M|9Mv   r3   r   ))
__future__r   r   r   type__metaclass__DOCUMENTATIONr{   rI   rp   rv   r   rC   rL   r    ImportErrorimp_excansible.errorsr   r   r   ansible.module_utils._textr	   r
   r   ansible.module_utils.sixr   ansible.plugins.connectionr   r    ansible.plugins.shell.powershellr   ansible.utils.displayr   	functoolsr   os.pathr   rS   rP   r    r3   r2   <module>r      s    C B"H         V V C C / > : )  
) lE1tL0dK/TJ/TJ0dK Z  Z 7  #"#s   B B, B''B,