code: def identify_cde_effect(
      graph: nx.DiGraph,
      action_nodes: List[str],
      outcome_nodes: List[str],
      observed_nodes: List[str],
      backdoor_adjustment: BackdoorAdjustment,
      estimand_type: EstimandType,
  ):
      """Identify controlled direct effect. For a definition, see Vanderwheele (2011).
      Controlled direct and mediated effects: definition, identification and bounds.
      https://www.ncbi.nlm.nih.gov/pmc/articles/PMC4193506/
  
      Using do-calculus rules, identification yields a adjustment set.
      It is based on the principle that under a graph where the direct edge from treatment
      to outcome is removed, conditioning on the adjustment set should d-separate
      treatment and outcome.
      """
      estimands_dict = {}
      # Pick algorithm to compute backdoor sets according to method chosen
      backdoor_sets = identify_backdoor(
          graph,
          action_nodes,
          outcome_nodes,
          observed_nodes,
          backdoor_adjustment,
          direct_effect=True,
      )
      (
          estimands_dict,
          backdoor_variables_dict,
      ) = build_backdoor_estimands_dict(
          action_nodes,
          outcome_nodes,
          observed_nodes,
          backdoor_sets,
          estimands_dict,
      )
      # Setting default "backdoor" identification adjustment set
      default_backdoor_id = get_default_backdoor_set_id(
          graph, action_nodes, outcome_nodes, backdoor_variables_dict
      )
      if len(backdoor_variables_dict) > 0:
          estimands_dict["backdoor"] = estimands_dict.get(
              str(default_backdoor_id), None
          )
          backdoor_variables_dict[
              "backdoor"
          ] = backdoor_variables_dict.get(
              str(default_backdoor_id), None
          )
      else:
          estimands_dict["backdoor"] = None
  
      # Finally returning the estimand object
      estimand = IdentifiedEstimand(
          None,
          treatment_variable=action_nodes,
          outcome_variable=outcome_nodes,
          estimand_type=estimand_type,
          estimands=estimands_dict,
          backdoor_variables=backdoor_variables_dict,
          instrumental_variables=None,
          frontdoor_variables=None,
          mediation_first_stage_confounders=None,
          mediation_second_stage_confounders=None,
          default_backdoor_id=default_backdoor_id,
      )
      return estimand
  
imports: import itertools
  import logging
  from enum import Enum
  from typing import Dict, List, Optional, Union
  import networkx
  import sympy
  import sympy.stats
  from dowhy.causal_identifier.efficient_backdoor import EfficientBackdoor
  from dowhy.causal_identifier.identified_estimand import IdentifiedEstimand
  from dowhy.graph import check_dseparation, check_valid_backdoor_set, check_valid_frontdoor_set, check_valid_mediation_set, do_surgery, get_all_directed_paths, get_backdoor_paths, get_descendants, get_instruments, has_directed_path
  from dowhy.utils.api import parse_state
label_desc: Use image node_id 3 for calling a global function with example usage: identify_cde_effect(graph, action_nodes, outcome_nodes, observed_nodes, backdoor_adjustment, estimand_type) and returns: estimand