a
    Sic                     @   s  d Z ddlZddlZddlZddlm  m  mZ ddlm  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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m#Z# ddl$m%Z% e%de& dZ'e%de& dZ(e%de& dZ)e%de& dZ*e%de& dZ+e%de& dZ,e%d e& d!Z-e%d"e& d#Z.e%d$e& d%Z/ej01ej2Z3e34ej5 dUd'd(Z6d)d* Z7d+d, Z8d-d. Z9d/d0 Z:G d1d2 d2Z;d3d4 Z<d5d6 Z=d7d8 Z>d9d: Z?d;d< Z@d=d> ZAd?d@ ZBdAdB ZCG dCdD dDZDdEdF ZEG dGdH dHZFdVdIdJZGdKdL ZHG dMdN dNeDZIdOdP ZJdQdR ZKdSdT ZLdS )Wz!Keras SavedModel deserialization.    Nmessage)backend)regularizers)
input_spec)optimizer_v2)saved_metadata_pb2)versions_pb2)saving_utils)	constants)
json_utils)utils)CommonEndpoints)generic_utils)layer_utils)metrics_utils)
tf_inspect)
LazyLoader
models_libzkeras.models
base_layerzkeras.engine.base_layerlayers_modulezkeras.layersinput_layerzkeras.engine.input_layerfunctional_libzkeras.engine.functionaltraining_libzkeras.engine.trainingtraining_lib_v1zkeras.engine.training_v1metricszkeras.metricsbase_rnnzkeras.layers.rnn.base_rnnTc              
   C   s^  t  }tjj| jd }|j}tjj	
| tj}tjjj	|rzFtjj	|d}| }W d   n1 st0    Y  || W q tjy }	 z td| d|	 W Y d}	~	qd}	~	0 0 ntd t|||  |jstjj| |dS t|}t||}
|
j|d d	di}|
j D ]\}}|||
 |< q$t!" 2 t!j#d
dd tjjj$| ||d}W d   n1 s0    Y  |
%  |
&  |d	 }t'|t(j)r,|r,|j*d +dd}|dur"|j,f i t-.|ddi t-/| t'|j0t1j2r,|j03 r,td n
td t4 sZt56 }|7tjj8tjjj9j: |S )a>  Loads Keras objects from a SavedModel.

    Any Keras layer or model saved to the SavedModel will be loaded back
    as Keras objects. Other objects are loaded as regular trackable objects
    (same as `tf.saved_model.load`).

    Currently, Keras saving/loading only retains the Keras object's weights,
    losses, and call function.

    The loaded model can be re-compiled, but the original optimizer, compiled
    loss functions, and metrics are not retained. This is temporary, and
    `model.save` will soon be able to serialize compiled models.

    Args:
      path: Path to SavedModel.
      compile: If true, compile the model after loading it.
      options: Optional `tf.saved_model.LoadOptions` object that specifies
        options for loading from SavedModel.

    Returns:
      Object loaded from SavedModel.
    r   rbNz$Cannot parse keras metadata at path z: Received error: a  SavedModel saved prior to TF 2.5 detected when loading Keras model. Please ensure that you are saving the model with model.save() or tf.keras.models.save_model(), *NOT* tf.saved_model.save(). To confirm, there should be a file named "keras_metadata.pb" in the SavedModel directory.)options)compilerootignorezTrying to load ShardedVariablesr   metadatatraining_configfrom_serializedTzYour optimizer uses slots. Slots cannot be restored from saved_model, as a result, your model is starting with  a new initialized optimizer.zcNo training configuration found in save file, so the model was *not* compiled. Compile it manually.);r   SavedMetadatatf__internal__saved_modelparse_saved_modelmeta_graphsobject_graph_defiogfilejoinr   SAVED_METADATA_PATHcompatv1ExistsGFilereadParseFromStringr   DecodeErrorIOErrorloggingwarning_read_legacy_metadatanodesload_update_to_current_versionKerasObjectLoaderload_layersloaded_nodesitemsget_pathwarningscatch_warningsfilterwarningsload_partialfinalize_objectsdel_tracking
isinstancer   Model_serialized_attributesgetr   r
   !compile_args_from_training_configtry_build_compiled_arguments	optimizerr   OptimizerV2get_slot_namesexecuting_eagerlyr   get_sessionrunget_collection	GraphKeysTABLE_INITIALIZERS)pathr   r   r"   meta_graph_defr+   path_to_metadata_pbffile_contentekeras_loadernodes_to_loadnode_idloaded_nodeloadedmodelr#   sess re   Y/var/www/html/django/DPS/env/lib/python3.9/site-packages/keras/saving/saved_model/load.pyr<   E   s    &

&




r<   c                 C   sn   | j D ]b}|jjdkr|jtjtjtjfv rt	|j
}|d}|dur|gi f|d< t ||_
q| S )zCApplies version updates to the metadata proto for backwards compat.   	save_specNfull_save_spec)r;   versionproducer
identifierr   MODEL_IDENTIFIERSEQUENTIAL_IDENTIFIERNETWORK_IDENTIFIERr   decoder"   rL   Encoderencode)r"   nodenode_metadatarh   re   re   rf   r=      s    

r=   c              	   C   s   t | }t| jD ]j\}}|ddkr|jjtjv r|jjsNt	d| d|jj
||| tjddg d|jj|jjd qdS )	z@Builds a KerasMetadata proto from the SavedModel ObjectGraphDef.kinduser_objectz2Unable to create a Keras model from SavedModel at z. This SavedModel was exported with `tf.saved_model.save`, and lacks the Keras metadata file. Please save your Keras model by calling `model.save` or `tf.keras.models.save_model`. Note that you can still load this SavedModel with `tf.saved_model.load`.rg   )rk   min_consumerbad_consumers)r`   	node_pathrj   rl   r"   N)_generate_object_paths	enumerater;   
WhichOneofrv   rl   r   KERAS_OBJECT_IDENTIFIERSr"   
ValueErroraddr	   
VersionDef)r+   r"   rX   
node_pathsr`   protore   re   rf   r:      s.    	r:   c                 C   sf   ddi}dg}|rb|  }|| }| j| jD ]0}|j|v r>q.d||j||j< ||j q.q|S )zKTraverses through an ObjectGraphDef and builds a map of all node
    paths.r   r    {}.{})popr;   childrenr`   format
local_nameappend)r+   pathsnodes_to_visitcurrent_nodecurrent_path	referencere   re   rf   rz      s    

rz   c                 C   s0   t | trdS t | tjr,| jp*t | tjS dS )z0Determines whether the layer is a graph network.F)rI   RevivedNetworkr   
Functional_is_graph_networkr   
Sequentiallayerre   re   rf   r     s    
r   c                   @   s   e Zd ZdZdd Zdd Zdd Zd+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dd Zdd Zdd  Zd!d" Zd#d$ Zd,d&d'Zd(d) Zd*S )-r>   ao  Loader that recreates Keras objects (e.g.

    layers, models).

    Layers and models are revived from either the config or SavedModel following
    these rules:
    1. If object is a graph network (i.e. Sequential or Functional) then it will
       be initialized using the structure from the config only after the
       children layers have been created. Graph networks must be initialized
       with inputs and outputs, so all child layers must be created beforehand.
    2. If object's config exists and the class can be found, then revive from
       config.
    3. Object may have already been created if its parent was revived from
       config. In this case, do nothing.
    4. If nothing of the above applies, compose the various artifacts from the
       SavedModel to create a subclassed layer or model. At this time, custom
       metrics are not supported.

    c                 C   sH   dd |j D | _|| _dd |j D | _i | _t | _i | _g | _d S )Nc                 S   s   i | ]}|j |qS re   )r`   .0xre   re   rf   
<dictcomp>&      z.KerasObjectLoader.__init__.<locals>.<dictcomp>c                 S   s   i | ]}|j |jqS re   )r`   ry   )r   	node_datare   re   rf   r   )  s   )	r;   	_metadata_proto_node_pathsr@   set_traversed_nodes_from_configmodel_layer_dependencies_models_to_reconstruct)selfr"   r+   re   re   rf   __init__%  s    zKerasObjectLoader.__init__c                 C   sx   | j  D ]h}|d }t|tjs$q
tD ]}|| q(t|tjr
t	|j
}|D ]}td|durR|| qRq
dS )zMRemoves tracked references that are only used when loading the
        model.r   ^layer(_with_weights)?-[\d+]N)r@   valuesrI   r   LayerPUBLIC_ATTRIBUTES_delete_trackingr   r   list$_self_unconditional_dependency_namesrematch)r   rs   namedependenciesre   re   rf   rH   :  s    

zKerasObjectLoader.del_trackingc                 C   s<  || j v rdS | j| }| j | |  t|tjrd|jsdt	| j
| j}| |||d g }|jD ]$}||j}|||j|jf qn| |tjdg}	|	durt|drdd |jD }
| jj|	 jD ]:}|
|j}|durdtj|j}|||j|f q|D ]\}}}| jj| }t|tjjjsHq|jj tjj!j"# v rttjj!j"$|j}n|j%tj&v rt'}nt(}|| j)v r| j)| d |urt*+d	| q|,d
dkr|j-j.r|j-j.d |_/t|tjjj0rdd }d||}|| j|< | 1||| ||f| j)|< qdS )z2Recursively records objects recreated from config.Nbuild_input_shapelayer_metrics_metricsc                 S   s   i | ]}|j |qS re   r   r   mre   re   rf   r   z  r   zIKerasObjectLoader._add_children_recreated_from_config.<locals>.<dictcomp>z{}.layer_metrics.{}r   zLooks like there is an object (perhaps variable or layer) that is shared between different layers/models. This may cause issues when restoring the variable values. Object: {}ru   variablez:0c                  W   s   d S Nre   )argsre   re   rf   <lambda>  r   zGKerasObjectLoader._add_children_recreated_from_config.<locals>.<lambda>r   )2r   r   r   _maybe_initialize_trackablerI   r   r   builtr   rp   r   r"   _try_build_layerrL   r   _lookup_dependencyr   r   r`   _search_for_child_noder   
KERAS_ATTRhasattrr   r   r;   r   r&   r'   tracking	Trackablerv   rl   r(   r<   registered_identifiers
get_setter_object_identifierr}   _revive_settersetattrr@   r8   r9   r|   r   r   _handle_nameTrackableDataStructure#_add_children_recreated_from_config)r   objr   r`   parent_pathr"   r   r   	obj_childmetric_list_node_idobj_metricsmetricmetric_pathchild_id
child_namechild_protosetter
child_pathre   re   rf   r   [  s    






z5KerasObjectLoader._add_children_recreated_from_configTc                 C   s   g }| j  D ]8}|jtjkr*|| q| |j|j|j| j	|j< q|D ]\}z | |j|j|j| j	|j< W qL t
y } z|r|td W Y d}~qLd}~0 0 qLdS )z'Load all layer nodes from the metadata.zUnable to restore custom metric. Please ensure that the layer implements `get_config` and `from_config` when saving. In addition, please use the `custom_objects` arg when calling `load_model()`.N)r   r   rl   r   METRIC_IDENTIFIERr   _load_layerr`   r"   r@   r~   r8   r9   )r   r   metric_listrt   r]   re   re   rf   r?     s.    
zKerasObjectLoader.load_layersc           	      C   s   t |}|| jv rx| j| \}}t|| |d}t|rpt|rp| |}||f| j	|< |sp| j
| ||fS | |||\}}|du rt||\}}t|| ||fS )z1Load a single layer from a SavedUserObject proto.configN)r   rp   r@    _maybe_add_serialized_attributesrL   r   r   validate_config_get_child_layer_node_idsr   r   r   _revive_from_configrevive_custom_object)	r   r`   rl   r"   rs   r   r   child_nodesr   re   re   rf   r     s$    





zKerasObjectLoader._load_layerc                 C   sd   |t jkr| |}n| |||p.| ||}|du r<dS | t}| || jj	| | ||fS )z3Revives a layer/model from config, or returns None.N)NN)
r   r   _revive_metric_from_config_revive_graph_network"_revive_layer_or_model_from_config_config_node_setterr   r   r   r;   )r   rl   r"   r`   r   r   re   re   rf   r     s    


z%KerasObjectLoader._revive_from_configc           	      C   s   | d}t|sdS tj|d }t|dur:dS | ddpT|dkpT|dk}|s^dS |dkrxtj|d d	}n,|t	j
krtj|d	}ntjg g |d d
}| |}||f| j|< |s| j| |S )z$Revives a graph network from config.r   N
class_nameis_graph_networkFr   r   r   r   )inputsoutputsr   )rL   r   r   r&   r0   as_strget_registered_objectr   r   r   rn   r   r   r   r   r   )	r   rl   r"   r`   r   r   !model_is_functional_or_sequentialrc   layersre   re   rf   r     s2    




z'KerasObjectLoader._revive_graph_networkc              
   C   s  | d}| d}| d}| d}t|s6dS zttj|||d}W n ttfy } z6t|}	|	rt	d| d|	 d	|n W Y d}~nDd}~0  t
y } z$|r|nW Y d}~dS W Y d}~n
d}~0 0 |d
 |_| ddur|d |_| ddur ||d  | ddur:|d |_| ddurT|d |_t|tjr| d}
|
dur|
\}}|d}|||| | d}| |||}|sdS |S )zMRevives a layer/custom model from config; returns None if
        infeasible.r   r   shared_object_idmust_restore_from_configN)r   z#Unable to restore object of class 'z9' likely due to name conflict with built-in Keras class 'z'. To override the built-in Keras definition of the object, decorate your class with `@keras.utils.register_keras_serializable` and include that file in your program, or pass your class in a `keras.utils.CustomObjectScope` that wraps this load call.r   	trainabledtypestatefulautocastri   r   r   )rL   r   r   r   deserialize serialize_keras_class_and_config	TypeErrorKeyErrorZget_builtin_layerRuntimeErrorr~   _namer   _set_dtype_policyr   	_autocastrI   r   rJ   r   _set_save_specr   )r   r"   r`   r   r   r   r   r   r]   Zbuiltin_layerri   	args_speckwargs_specinputs_specr   r   re   re   rf   r   ;  s^    






$







z4KerasObjectLoader._revive_layer_or_model_from_configc                 C   s~   t j|d }|d}t|s(dS ztt||}W n t	yR   Y dS 0 |d}|durzt
|drz|| |S )z?Revives a metric object using the config saved in the metadata.r   r   Nr   _build)r&   r0   r   rL   r   r   r   r   r   r~   r   r   )r   r"   r   r   r   r   re   re   rf   r     s     



z,KerasObjectLoader._revive_metric_from_configc                 C   sZ   |j st|jdrd|_ dS |du r2| j|dd}|durV|| tj|| dS dS )zAttempts to build the layer._is_defaultTNconvert_to_shapesF)r   r   build_infer_inputsr   r   )r   r   r`   r   re   re   rf   r     s    
z"KerasObjectLoader._try_build_layerc                 C   s
   | j | S r   )r   )r   r`   re   re   rf   rB     s    zKerasObjectLoader.get_pathc                 C   s   g }g }| j  D ]r\}\}}t|tjr|| jv r6q| || t|tjrRqnt|t	j
r`qt|ttfrz|| q|| qt| t| |   dS )a  Finish setting up Keras objects.

        This function is executed after all objects and functions have been
        created.  Call functions and losses are attached to each layer, and once
        all layers have been fully set up, graph networks are initialized.

        Subclassed models that are revived from the SavedModel are treated like
        layers, and have their call/loss functions attached here.
        N)r@   rA   rI   r   r   r   _unblock_model_reconstructionr   
InputLayerr   MetricRevivedLayerRevivedInputLayerr   _finalize_saved_model_layers_finalize_config_layers_reconstruct_all_models)r   layers_revived_from_configlayers_revived_from_saved_modelr`   rs   _re   re   rf   rG     s&    
z"KerasObjectLoader.finalize_objectsc                 C   sV   | j  D ]F\}}|\}}||vr$q
||||< tdd |D r
| j| q
dS )z1Removes layer from blocking model reconstruction.c                 s   s   | ]}t |tjV  qd S r   )rI   r   r   r   re   re   rf   	<genexpr>  r   zBKerasObjectLoader._unblock_model_reconstruction.<locals>.<genexpr>N)r   rA   indexallr   r   )r   layer_idr   model_idvr  r   re   re   rf   r    s    z/KerasObjectLoader._unblock_model_reconstructionc                    s   t  } jrJ jd}||  j| \}} ||| t|g q|t  j krt  j | } fdd|D }td| dS )z1Reconstructs the network structure of all models.r   c                    s   g | ]} j | d  jqS )r   )r   r   )r   r  r   re   rf   
<listcomp>  s   z=KerasObjectLoader._reconstruct_all_models.<locals>.<listcomp>zbError loading model(s) in the SavedModel format. The following model(s) could not be initialized: N)	r   r   r   r   r   _reconstruct_modelr	  keysr~   )r   all_initialized_modelsr  rc   r   uninitialized_model_idsuninitialized_model_namesre   r  rf   r
    s(    

z)KerasObjectLoader._reconstruct_all_modelsc              	   C   s  t | j| jd }|jr n^t|tjr@|rBt|d tj	s|d d d dkrx|
dtj	|d d d  n^d|d d d v r|d d d d }|
dtj	|dd |d |d j|d jd	 d
 |j||d d |js~| |d }| |}| j|dd}|| |js~t|ts~|| n>tj|dd |D d\}	}
}|j|	|
|d d t|| t| | || dS )z#Reconstructs the network structure.r   r   r   r   r  batch_input_shaperg   N_input)input_shape
batch_sizer   r   r   r   Tr   c                 S   s   i | ]}|j |qS re   r   )r   r   re   re   rf   r   /  r   z8KerasObjectLoader._reconstruct_model.<locals>.<dictcomp>)created_layers)r   rp   r   r"   r   rI   r   r   r   r  insertfrom_configr   r   r   r   r  _set_inputsr   dictr  r   reconstruct_from_configconnect_ancillary_layers%_set_network_attributes_from_metadatar  )r   r  rc   r   r   r  first_layerinput_specsinput_shapesr   r   r  re   re   rf   r     s\    
	

z$KerasObjectLoader._reconstruct_modelc           
      C   s   d}i }t d}| jj| jD ]@}||j}|du r:q t|d}t	|d |}|j
||< q g }t|D ]$}	||	}|du r q|| qn|S )zLReturns the node ids of each layer in a Sequential/Functional
        model.r   zlayer-(\d+)Nrg   )r   r   r   r;   r   r   r   intgroupmaxr`   rangerL   r   )
r   r`   
num_layerschild_layerspatternchildr   layer_norderednre   re   rf   r   :  s"    

z+KerasObjectLoader._get_child_layer_node_idsc                 C   sH   |s|S | j j| jD ],}|j|d kr| |j|dd   S qdS )a  Returns node id of child node.

        A helper method for traversing the object graph proto.

        As an example, say that the object graph proto in the SavedModel
        contains an object with the following child and grandchild attributes:

        `parent.child_a.child_b`

        This method can be used to retrieve the node id of `child_b` using the
        parent's node id by calling:

        `_search_for_child_node(parent_id, ['child_a', 'child_b'])`.

        Args:
          parent_id: node id of parent node
          path_to_child: list of children names.

        Returns:
          node_id of child, or None if child isn't found.
        r   rg   N)r   r;   r   r   r   r`   )r   	parent_idpath_to_childr1  re   re   rf   r   S  s    
z(KerasObjectLoader._search_for_child_nodeFc           	      C   s   |  |dg}|du rdS | jj| jj}|s2dS |d }| jj| }tjj|j	}|d d }|rxtj
dd |S |S dS )z6Infers input shape of layer from SavedModel functions.&call_and_return_all_conditional_lossesNr   c                 S   s   | j S r   )shape)specre   re   rf   r     r   z1KerasObjectLoader._infer_inputs.<locals>.<lambda>)r   r   r;   functionconcrete_functionsr&   r'   r(   decode_protocanonicalized_input_signaturenestmap_structure)	r   layer_node_idr   
call_fn_idr;  call_fn_namecall_fn_protostructured_input_signaturer   re   re   rf   r  s  s&    zKerasObjectLoader._infer_inputsc                    s    fdd}|S )z7Creates edges for nodes that are recreated from config.c                    s   |  |d u r | || d S r   )r   )r   r   valuer   re   rf   setattr_wrapper  s    z>KerasObjectLoader._config_node_setter.<locals>.setattr_wrapperre   )r   r   rG  re   rF  rf   r     s    z%KerasObjectLoader._config_node_setterN)T)F)__name__
__module____qualname____doc__r   rH   r   r?   r   r   r   r   r   r   rB   rG   r  r
  r  r   r   r  r   re   re   re   rf   r>     s(   ![
&#*K*
: 
r>   c           	      C   s`  | D ]}d|_ tt|dd}|rv|jrvtt|}tj	|||dd|_
|jd d }d|jjv rjd}|| qtt||_
q| D ]}t|trBt| tt|drBt|j}|jsq|jdu rt|\}}t|}|d}n|j}t|}|d}d}|||| td	d
 tj||gD sB| | t!| t"| t#| qdS )z=Runs the final steps of loading Keras Layers from SavedModel.T"call_and_return_conditional_lossesN)return_methodr"   expects_training_argtrainingr   c                 s   s   | ]}t |tjV  qd S r   )rI   r&   
TensorSpecr   re   re   rf   r    s   z/_finalize_saved_model_layers.<locals>.<genexpr>)$r   getattr_get_keras_attrr;  r   CallFunctionSpecr   getfullargspecr   use_wrapped_callcallrK   function_spec	arg_names_init_call_fn_argstypes
MethodType0_unable_to_call_layer_due_to_serialization_issuerI   r   r&  r   rL  input_signature(infer_inputs_from_restored_call_functionr   r   r   anyr&   r>  flattenr"  #_restore_layer_unconditional_losses_restore_layer_activation_loss_restore_layer_metrics)	r   r   
layer_call	call_specrN  call_fnr   kwargsr   re   re   rf   r    sd    





r  c                 O   s    t d| j dt|  ddS )a  Replaces the `layer.call` if the layer was not fully serialized.

    Keras Model/Layer serialization is relatively relaxed because SavedModels
    are not always loaded back as keras models. Thus, when there is an issue
    tracing a non-signature function, a warning is logged instead of raising an
    error. This results in a SavedModel where the model's call function is
    saved, but the internal layer call functions are not.

    When deserialized with `tf.keras.models.load_model`, the internal layers
    which do not have serialized call functions should raise an error when
    called.

    Args:
      layer: Layer without the serialized call function.

    Raises:
      ValueError
    zCannot call custom layer z	 of type a  , because the call function was not serialized to the SavedModel.Please try one of the following methods to fix this issue:

(1) Implement `get_config` and `from_config` in the layer/model class, and pass the object to the `custom_objects` argument when loading the model. For more details, see: https://www.tensorflow.org/guide/keras/save_and_serialize

(2) Ensure that the subclassed model or layer overwrites `call` and not `__call__`. The input shape and dtype will be automatically recorded when the object is called, and used when saving. To manually specify the input shape/dtype, decorate the call function with `@tf.function(input_signature=...)`.N)r~   r   type)r   unused_argsunused_kwargsre   re   rf   r\    s    r\  c                 C   s   | D ]|}t |rt| t| t| t|tjrx|jrxtt	|drxt
t	|dd|_tj|jD ]}t| qh|  qdS )z9Runs the final steps of loading Keras Layers from config.statesN)r   ra  rb  rc  rI   r   RNNr   r   rR  rQ  rk  r&   r>  r`  r   track_variablefinalize_state)r   r   r   re   re   rf   r	    s    
r	  c                 C   s&   t t| jj| | _| jj| _d S r   )rZ  r[  r   update_state_wrapper	keras_apiupdate_stateresult)r   re   re   rf   _finalize_metric)  s
    rs  c                 C   sF   t t| dr tt| dg }n| jdg }|D ]}| | q2dS )z-Restore unconditional losses from SavedModel.layer_regularization_lossesregularization_lossesN)r   rR  rQ  rK   rL   add_loss)r   losseslossre   re   rf   ra  1  s    
ra  c                 C   s<   t t| dd}|r8| js8z
|| _W n ty6   Y n0 dS )z'Restore actiation loss from SavedModel.activity_regularizer_fnN)rQ  rR  activity_regularizerAttributeError)r   rz  re   re   rf   rb  @  s    


rb  c                 C   s   t jj rtj}ntj}tjt	t
jftjttjftjt|ftjttjftjttjfi}|| d}|dur||  }tt j|d |i }||S td|  ddS )zRevives object from SavedModel.Nr   z(Unable to restore custom object of type z. Please make sure that any custom layers are included in the `custom_objects` arg when calling `load_model()` and make sure that all layers implement `get_config` and `from_config`.)r&   r0   r1   #executing_eagerly_outside_functionsr   rJ   r   r   INPUT_LAYER_IDENTIFIERr  r   r  LAYER_IDENTIFIERr  r   r   rm   r   ro   r   r   rn   r   r   rL   rh  r   _init_from_metadatar~   )rl   r"   model_classrevived_classesparent_classesrevived_clsre   re   rf   r   Q  s8    


r   c                 C   sJ   t t| di }dd | jD }| D ]\}}||vr(| j| q(d S )Nr   c                 S   s   i | ]}|j |qS re   r   r   re   re   rf   r   {  r   z*_restore_layer_metrics.<locals>.<dictcomp>)rQ  rR  r   rA   r   )r   metrics_listr   r   r   re   re   rf   rc  y  s
    rc  c                   @   s0   e Zd ZdZedd Zedd Zdd ZdS )	r  z%Keras layer loaded from a SavedModel.c                 C   sX  t |d |d d}|ddur.|d |d< |ddurH|d |d< | f i |}t| |d |j_|d}t|r||_|d	durt	|d	 d
t
jid|_
|ddurt|d |_|ddur|d |_|ddur|d |_|ddur|d |_|ddur0|d |_W d   n1 sF0    Y  |tfS )zBCreate revived layer from metadata stored in the SavedModel proto.r   r   )r   r   r   Nr  rN  r   r   	InputSpecmodule_objectsrz  _is_feature_layerr   r   "preserve_input_structure_in_config)r#  rL   r   &no_automatic_dependency_tracking_scope
_call_specrN  r   r   _config$recursively_deserialize_keras_objectr   r  r   r   rz  r  r   r   #_preserve_input_structure_in_configr   )clsr"   	init_argsrevived_objr   re   re   rf   r    sB    




&z RevivedLayer._init_from_metadatac                 C   s   | j tjd S r   )rK   rL   r   r   r  re   re   rf   rp    s    zRevivedLayer.keras_apic                 C   s   t | dr| jS td S )Nr  )r   r  NotImplementedErrorr  re   re   rf   
get_config  s    
zRevivedLayer.get_configN)	rH  rI  rJ  rK  classmethodr  propertyrp  r  re   re   re   rf   r    s   
(
r  c                 C   s   |t v r2t|tjjjr&| j||d || j|< nLt| tj	r`t
d|dur`| j||dd nt| |ddurrnt| || dS )zBSetter function that saves some attributes to separate dictionary.r   r   NT)	overwrite)r   rI   r&   r'   r   r   _track_trackablerK   r   r   r   r   rQ  r   )r   r   rE  re   re   rf   r     s    
r   c                   @   s$   e Zd ZdZedd Zdd ZdS )r  z$InputLayer loaded from a SavedModel.c                 C   sp   t |d |d |d |d |d d}| f i |}t| |d |_W d   n1 s^0    Y  |tfS )	z/Revives the saved InputLayer from the Metadata.r   r   sparseraggedr  )r   r   r  r  r  r   N)r#  r   r  r  r   )r  r"   r  r  re   re   rf   r    s    (z%RevivedInputLayer._init_from_metadatac                 C   s   | j S r   )r  r  re   re   rf   r    s    zRevivedInputLayer.get_configN)rH  rI  rJ  rK  r  r  r  re   re   re   rf   r    s   
r  c                    sh   t  tr6d v r tj dS  fdd D S n.t  ttfrVfdd D S td  dS )	z1Deserialize Keras object from a nested structure.r   r  c                    s   i | ]}|t  | qS re   r  )r   keyr   r  re   rf   r     s   z8recursively_deserialize_keras_object.<locals>.<dictcomp>c                    s   g | ]}t | qS re   r  r   r  re   rf   r    s   z8recursively_deserialize_keras_object.<locals>.<listcomp>zdUnable to decode Keras layer config. Config should be a dictionary, tuple or list. Received: config=N)rI   r#  r   deserialize_keras_objecttupler   r~   r  re   r  rf   r    s"    

r  c                 C   sB   dd }| j d j}| j dd D ]}|j}tj|||}q"|S )a6  Returns TypeSpec of inputs from a restored call function.

    Args:
      fn: Restored layer call function. It is assumed that `fn` has at least one
        concrete function and that the inputs are in the first argument.

    Returns:
      TypeSpec of call function inputs in the form of (args, kwargs)
    c                 S   sF   t | tjs| S |  | g}|d u rBtd|  d| d|S )NzNo common supertype of z and .)rI   r&   TypeSpec_without_tensor_namesmost_specific_common_supertyper   )r   yrr  re   re   rf   common_spec  s    z=infer_inputs_from_restored_call_function.<locals>.common_specr   rg   N)r;  rD  r&   r>  r?  )fnr  r9  concretespec2re   re   rf   r^    s    r^  c                   @   s   e Zd ZdZedd ZdS )r   z1Keras network of layers loaded from a SavedModel.c                 C   s   | |d d}t |T |d |j_|d}t|r@||_|ddur^t	|d |_
W d   n1 sr0    Y  |tfS )zLCreate revived network from metadata stored in the SavedModel
        proto.r   r   rN  r   rz  N)r   r  r  rN  rL   r   r   r  r   r   rz  r   )r  r"   r  r   re   re   rf   r  0  s    

$z"RevivedNetwork._init_from_metadataN)rH  rI  rJ  rK  r  r  re   re   re   rf   r   -  s   r   c                 C   s^   t | @ | jd }|ddur2| |d  |d | _W d   n1 sP0    Y  dS )z)Sets attributes recorded in the metadata.r"   r   Nr   )r   r  rK   rL   r   
_trainable)r  r"   re   re   rf   r&  J  s
    
r&  c                 C   sB   t | ds>t|  d|i| _W d    n1 s40    Y  d S )NrK   r"   )r   r   r  rK   )r   r"   re   re   rf   r   T  s    
r   c                 C   s   t | di tjd S )NrK   )rQ  rL   r   r   r   re   re   rf   rR  ]  s    rR  )TN)N)MrK  r   rZ  rC   tensorflow.compat.v1.loggingr0   r1   r8   tensorflow.compat.v2v2r&   google.protobufr   kerasr   r   keras.enginer   keras.optimizers.optimizer_v2r   Zkeras.protobufr   r	   keras.savingr
   keras.saving.saved_modelr   r   r   Z.keras.saving.saved_model.serialized_attributesr   keras.utilsr   r   r   r   keras.utils.generic_utilsr   globalsr   r   r   r   r   r   r   r   r   all_functionsunionall_checkpointable_objectsr   r   r   r<   r=   r:   rz   r   r>   r  r\  r	  rs  ra  rb  r   rc  r  r   r  r  r^  r   r&  r   rR  re   re   re   rf   <module>   s   
z      J&#(7 
 
	