code: def PPOLoss(
      dist_class,
      actions,
      curr_logits,
      behaviour_logits,
      advantages,
      value_fn,
      value_targets,
      vf_preds,
      cur_kl_coeff,
      entropy_coeff,
      clip_param,
      vf_clip_param,
      vf_loss_coeff,
      clip_loss=False,
  ):
      def surrogate_loss(
          actions,
          curr_dist,
          prev_dist,
          advantages,
          clip_param,
          clip_loss,
      ):
          pi_new_logp = curr_dist.logp(actions)
          pi_old_logp = prev_dist.logp(actions)
  
          logp_ratio = tf.math.exp(pi_new_logp - pi_old_logp)
          if clip_loss:
              return tf.minimum(
                  advantages * logp_ratio,
                  advantages
                  * tf.clip_by_value(
                      logp_ratio, 1 - clip_param, 1 + clip_param
                  ),
              )
          return advantages * logp_ratio
  
      def kl_loss(curr_dist, prev_dist):
          return prev_dist.kl(curr_dist)
  
      def entropy_loss(dist):
          return dist.entropy()
  
      def vf_loss(value_fn, value_targets, vf_preds, vf_clip_param=0.1):
          # GAE Value Function Loss
          vf_loss1 = tf.math.square(value_fn - value_targets)
          vf_clipped = vf_preds + tf.clip_by_value(
              value_fn - vf_preds, -vf_clip_param, vf_clip_param
          )
          vf_loss2 = tf.math.square(vf_clipped - value_targets)
          vf_loss = tf.maximum(vf_loss1, vf_loss2)
          return vf_loss
  
      pi_new_dist = dist_class(curr_logits, None)
      pi_old_dist = dist_class(behaviour_logits, None)
  
      surr_loss = tf.reduce_mean(
          surrogate_loss(
              actions,
              pi_new_dist,
              pi_old_dist,
              advantages,
              clip_param,
              clip_loss,
          )
      )
      kl_loss = tf.reduce_mean(kl_loss(pi_new_dist, pi_old_dist))
      vf_loss = tf.reduce_mean(
          vf_loss(value_fn, value_targets, vf_preds, vf_clip_param)
      )
      entropy_loss = tf.reduce_mean(entropy_loss(pi_new_dist))
  
      total_loss = -surr_loss + cur_kl_coeff * kl_loss
      total_loss += (
          vf_loss_coeff * vf_loss - entropy_coeff * entropy_loss
      )
      return total_loss, surr_loss, kl_loss, vf_loss, entropy_loss
  
imports: import logging
  from typing import Dict, List, Type, Union
  from ray.rllib.algorithms.ppo.ppo_tf_policy import validate_config
  from ray.rllib.evaluation.postprocessing import Postprocessing, compute_gae_for_sample_batch
  from ray.rllib.models.modelv2 import ModelV2
  from ray.rllib.models.tf.tf_action_dist import TFActionDistribution
  from ray.rllib.models.utils import get_activation_fn
  from ray.rllib.policy.dynamic_tf_policy_v2 import DynamicTFPolicyV2
  from ray.rllib.policy.eager_tf_policy_v2 import EagerTFPolicyV2
  from ray.rllib.policy.sample_batch import SampleBatch
  from ray.rllib.policy.tf_mixins import LocalOptimizer, ModelGradients, ValueNetworkMixin, compute_gradients
  from ray.rllib.utils import try_import_tf
  from ray.rllib.utils.annotations import override
  from ray.rllib.utils.typing import TensorType
label_desc: Use image node_id 1 for calling a global function with example usage: PPOLoss(dist_class, actions, curr_logits, behaviour_logits, advantages, value_fn, value_targets, vf_preds, cur_kl_coeff, entropy_coeff, clip_param, vf_clip_param, vf_loss_coeff, clip_loss) and returns: total_loss,  surr_loss,  kl_loss,  vf_loss,  entropy_loss, unknown, prev_dist, dist, vf_loss, tf