
    .                         S r SSKrSSKrSSKrSSKrSSKrSSKJr  SSKJr  SSK	J
r
  SSK	Jr  SSKJr  SSKrSrS	rS
rSr\" S5      \-
  rSrSrSrSrSrS rS rS rS rS r " S S\5      r SS jr!g)zFUtilities for handling YAML schemas for gcloud export/import commands.    N)log)yaml)resource_projector)yaml_printer)filesz6A gcloud export/import command YAML validation schema.P   (      zdescription: z<YAML-WORKAROUND/>z	Optional.z	Required.z"^(?:\[Output Only\]|Output only\.)zRy|Y|yes|Yes|YES|n|N|no|No|NO|true|True|TRUE|false|False|FALSE|on|On|ON|off|Off|OFFc                    [         U [        -  -
  n[        R                  " U[	        [
        U5      5      n[        U5      S:w  a  SR                  U5      $ US   nU[        U5      [        -   -
  nUS:  a  US-   US-  -   [        -   $ U$ )a%  Returns description: |- text wrapped so it won't exceed _WIDTH at depth.

The YAML representer doesn't seem to take the length of the current tag
into account when deciding whether to inline strings or use |-. In this case
the tag is always "description: ". This function detects when YAML would fail
and adds temporary marker lines to produce the desired output. The marker
lines are removed prior to final output.

Args:
  depth: The nested dict depth.
  text: The text string to wrap.

Returns:
  Text wrapped so it won't exceed _WIDTH at depth.
   
r    )
_WIDTH_INDENTtextwrapwrapmax_MINWRAPlenjoin_DESCRIPTION_INDENT_YAML_WORKAROUND)depthtextwidthlineslinenudges         2lib/googlecloudsdk/command_lib/util/apis/export.py_WrapDescriptionr    1   s      EGO
$%
--c(E2
3%Z1_99U	q$
3t922
3%
QY $;$'777	+    c                 4   [         R                  " U 5      R                  5       n[        R                  " SU5      (       a  g[        R                  " SU5      (       a  g[        R                  " SU5      (       a  gUS:X  a  gUS:X  a  gUS:X  a  g	US
:X  a  gU$ )z6Returns the JSON schema normalized type name for name.z.?int64integerz.?int32z^int\d*$floatnumberdoubleboolbooleanbytesstring)six	text_typelowerrematch)namess     r   _NormalizeTypeNamer2   O   s    	mmD!!XXj!XXj!XXk1'\(]&['\	
(r!   c                     U R                  S0 5      R                  S0 5      R                  S0 5      R                  S0 5      R                  SS5      nUS:H  $ )a%  Returns whether the field represents a google.protobuf.Struct message.

google.protobuf.Struct is the following message:
  message Struct {
    // Unordered map of dynamically typed values.
    map<string, Value> fields = 1;
  }

In apitools, this corresponds to a message with an additionalProperties
field containing a list of AdditionalProperty messages each of which holds a
key/value pair, where the value is a extra_types.JsonValue message.

Args:
  field: A message spec field dict.
Returns:
  True iff the field is a google.protobuf.Struct.
fieldsadditionalPropertiesvaluetype 	JsonValue)get)fieldmaybe_map_value_types     r   _IsProtobufStructFieldr=   c   sc    $ C
 "&&)c'C2"sb "	  
	,,r!   c                     / n[         R                  " U 5       H?  u  p#US   nUS:w  d  M  UR                  [        5      (       d  M.  UR	                  U5        MA     U$ )zReturns the list of required field names in fields.

Args:
  fields: A message spec fields dict.

Returns:
  The list of required field names in fields.
descriptionr5   )r+   	iteritems
startswith	_REQUIREDappend)r4   requiredr0   r6   r?   s        r   _GetRequiredFieldsrE   ~   sV     (]]6*kd&K %%+*@*@*K*Kood + 
/r!   c                 F    [        U5      nU(       a  [        U5      U S'   gg)zAdds required fields to spec.rD   N)rE   sorted)specr4   rD   s      r   _AddRequiredFieldsrI      s#    '(h'D r!   c                   @    \ rS rSrSrSS jrS rS rS rS r	S	 r
S
rg)ExportSchemasGenerator   z>Recursively generates export JSON schemas for nested messages.Nc                 :    Xl         X l        [        5       U l        g N)_api
_directoryset
_generated)selfapi	directorys      r   __init__ExportSchemasGenerator.__init__   s    IOeDOr!   c                     US-   $ )z4Returns the schema file name given the message name.z.yaml )rS   message_names     r   _GetSchemaFileName)ExportSchemasGenerator._GetSchemaFileName   s    '!!r!   c                     U R                  U5      nU R                  (       a*  [        R                  R	                  U R                  U5      nU$ )z9Returns the schema file path name given the message name.)r[   rP   ospathr   )rS   rZ   	file_paths      r   _GetSchemaFilePath)ExportSchemasGenerator._GetSchemaFilePath   s7    ''5I'',,t	:ir!   c                     [         R                  " 5       nUR                  S5        [        R                  " S[
        R                  " 5       US9R                  U5        [        R                  " SR                  [        5      SUR                  5       5      nU R                  U5      n[        R                  " SR                  U5      5        [         R"                  " U5       nUR                  U5        SSS5        g! , (       d  f       g= f)z;Writes the schema in spec to the _GetSchemaFilePath() file.z4$schema: "http://json-schema.org/draft-06/schema#"

r   )r0   	projectoroutz
 *{}
r   zGenerating JSON schema [{}].N)ioStringIOwriter   YamlPrinterr   IdentityProjectorPrintr.   subformatr   getvaluera   r   infor   
FileWriter)rS   rZ   rH   tmpcontentr`   ws          r   _WriteSchema#ExportSchemasGenerator._WriteSchema   s    
++-CIIFG$668 tffZ&&'78$OG''5IHH+229=>			)	$ggg 
%	$	$s   $C??
Dc                    US-  n[        [        R                  " U5      5       GH  u  pVUS   R                  5       nUR	                  [
        5      (       a!  U[        [
        5      S R                  5       nO:UR	                  [        5      (       a   U[        [        5      S R                  5       n[        R                  " [        U5      (       a  M  [        R                  " 5       nXU'   [        X5      US'   UR                  S5      (       a6  SUS'   [        R                  " UR                  S0 5      5      n	XS'   U	nUS-  n[        UR                  S5      [         5      n
UR                  SS5      nUR                  S	0 5      nU
(       a  US
:X  a:  X5	 [        R                  " 5       nU R#                  XX5        U(       a  XU'   GM  GM  [%        U5      (       a  SUS'   GM  U R'                  U5      US'   U R)                  X5        GM  XR*                  ;   a  U R'                  U5      US'   GM  [-        U5      nUS:X  a  UR                  S5      nSUS'   [        [        R                  " U5       VVs/ s H>  u  nn[        R.                  " [0        U5      (       a  [2        R4                  " U5      OUPM@     snn5      US'   GM  XS'   GM     gs  snnf )zAdds message fields to the YAML spec.

Args:
  depth: The nested dict depth.
  parent: The parent spec (nested ordered dict to add fields to) of spec.
  spec: The nested ordered dict to add fields to.
  fields: A message spec fields dict to add to spec.
r
   r?   Nrepeatedarrayr7   itemsr(   r4   r5   objectz$refenumchoicesr*   )rG   r+   r@   striprA   	_OPTIONALr   rB   r.   r/   _OUTPUT_ONLY_REGEXcollectionsOrderedDictr    r:   
isinstancestr
_AddFieldsr=   r[   GeneraterR   r2   	fullmatch_YAML_BOOLEAN_REGEXr   SingleQuotedScalarString)rS   r   parentrH   r4   r0   r6   r?   dry   is_message_field	type_name	subfields
propertiesr{   n_s                    r   r   !ExportSchemasGenerator._AddFields   ss    
QJEcmmF34-(..0k					*	*!#i./288:!!),,!#i./288:	$k	2	2

!
!
#a4j)%=a	:		&	''		'2(>?'


 $EIIf$5s;))FI.i))Hb)i	))j"..0*
//%J
:%4L #E** !F) --i8!F)
--	
-'--i8!F)(3)& 99Y'D AfI  MM$/  0DAq << 3Q77 --a0=>?/  AfI "fIu 5h s   =AKc                    XR                   ;   a  gU R                   R                  U5        [        R                  " 5       nSR	                  U R
                  R                  U R
                  R                  U5      US'   [        US'   SUS'   [        X25        SUS'   [        R                  " 5       nXCS	'   SS
0n[        R                  " 5       nXdS'   SUS'   SUS'   SUS'   [        R                  " 5       nXvS	'   [        R                  " U5      US'   [        R                  " U5      US'   [        R                  " U5      US'   [        R                  " U5      US'   [        R                  " U5      US'   [        R                  " 5       nXS'   SUS'   SUS'   XXS'   U R                  SX4U5        U R                  X5        g)aY  Recursively generates export/import YAML schemas for message_spec.

The message and nested messages are generated in separate schema files in
the destination directory. Pre-existing files are silently overwritten.

Args:
  message_name: The API message name for message_spec.
  message_spec: An arg_utils.GetRecursiveMessageSpec() message spec.
Nz{} {} {} export schematitler?   rz   r7   Fr5   r   r*   COMMENTz-User specified info ignored by gcloud import.ztemplate-idregiondateversionUNKNOWNrx   z+Unknown API fields that cannot be imported.ry   r   )rR   addr   r   rm   rO   r0   r   _SPEC_DESCRIPTIONrI   r   rt   )	rS   rZ   message_specrH   r   type_stringcommentcomment_propertiesunknowns	            r   r   ExportSchemasGenerator.Generate  s    &OO% ""$D,33				))<9DM+DDLt*#(D	 ((*J#8$K %%'G#yGFOLGM&+G"#$002.L(3(?(?(L}%#.#:#:;#Gx (3(?(?(L}%!,!8!8!Ev$/$;$;K$Hy! %%'G#yGFOJGM"GOOAt6l)r!   )rO   rP   rR   rN   )__name__
__module____qualname____firstlineno____doc__rV   r[   ra   rt   r   r   __static_attributes__rY   r!   r   rK   rK      s%    F
"D"L6*r!   rK   c                 8    [        X5      R                  X5        g)a  Recursively generates export/import YAML schemas for message_spec in api.

The message and nested messages are generated in separate schema files in the
current directory. Pre-existing files are silently overwritten.

Args:
  api: An API registry object.
  message_name: The API message name for message_spec.
  message_spec: An arg_utils.GetRecursiveMessageSpec() message spec.
  directory: The path name of the directory to place the generated schemas,
    None for the current directory.
N)rK   r   )rT   rZ   r   rU   s       r   GenerateExportSchemasr   <  s     (11,Mr!   rN   )"r   r   rf   r^   r.   r   googlecloudsdk.corer   r   googlecloudsdk.core.resourcer   r   googlecloudsdk.core.utilr   r+   r   r   r   r   r   r   r   r~   rB   r   r   r    r2   r=   rE   rI   rz   rK   r   rY   r!   r   <module>r      s     M  	 	 	  # $ ; 5 * 
 M 	
/*W4 ' 		: k <(-6.(]*V ]*@Nr!   