class_docstr: cluster
  
  This is meant as a thin wrapper around GKE clusters and the raw kubernetes
  python api, mainly to provide a simple interface for the most common
  cluster tasks.
class_docstr_tok: ["cluster","This","is","meant","as","a","thin","wrapper","around","GKE","clusters","and","the","raw","kubernetes","python","api",",","mainly","to","provide","a","simple","interface","for","the","most","common","cluster","tasks","."]
docstr: generates cluster create request
  
  Args:
  cluster_api: cluster api client
  creds: credentials
  cluster_name: name of cluster to create
  project_id: project id
  zone: zone in which to create cluster
        For a single-zone cluster (see below), this zone will contain the
        cluster control plane and all worker nodes. For a multi-zone cluster
        this zone will contain the control plane, but worker nodes can be
        created in any zone in the same region as the control plane.
  release_channel: release channel for cluster
  single_zone: create a single-zone cluster if true, multi-zone otherwise.
               A single-zone cluster only creates worker nodes in the same
               zone as the cluster control-plane (specified in the 'zone'
               argument above), whereas a multi-zone cluster can create
               worker nodes in every zone in the same region as the
               cluster control plane. A multi-zone cluster can help
               job response time when a given zone becomes overburdened.
  
  Returns:
  HttpRequest on success, None otherwise
docstr_tok: ["generates","cluster","create","request","Args",":","cluster_api",":","cluster","api","client","creds",":","credentials","cluster_name",":","name","of","cluster","to","create","project_id",":","project","id","zone",":","zone","in","which","to","create","cluster","For","a","single-zone","cluster","(","see","below",")",",","this","zone","will","contain","the","cluster","control","plane","and","all","worker","nodes",".","For","a","multi-zone","cluster","this","zone","will","contain","the","control","plane",",","but","worker","nodes","can","be","created","in","any","zone","in","the","same","region","as","the","control","plane",".","release_channel",":","release","channel","for","cluster","single_zone",":","create","a","single-zone","cluster","if","true",",","multi-zone","otherwise",".","A","single-zone","cluster","only","creates","worker","nodes","in","the","same","zone","as","the","cluster","control-plane","(","specified","in","the","'zone'","argument","above",")",",","whereas","a","multi-zone","cluster","can","create","worker","nodes","in","every","zone","in","the","same","region","as","the","cluster","control","plane",".","A","multi-zone","cluster","can","help","job","response","time","when","a","given","zone","becomes","overburdened",".","Returns",":","HttpRequest","on","success",",","None","otherwise"]
code: def create_request(
      cluster_api: discovery.Resource,
      creds: Credentials,
      cluster_name: str,
      project_id: str,
      zone: str,
      release_channel: ReleaseChannel,
      single_zone: bool,
  ) -> Optional[HttpRequest]:
      """generates cluster create request
  
      Args:
      cluster_api: cluster api client
      creds: credentials
      cluster_name: name of cluster to create
      project_id: project id
      zone: zone in which to create cluster
            For a single-zone cluster (see below), this zone will contain the
            cluster control plane and all worker nodes. For a multi-zone cluster
            this zone will contain the control plane, but worker nodes can be
            created in any zone in the same region as the control plane.
      release_channel: release channel for cluster
      single_zone: create a single-zone cluster if true, multi-zone otherwise.
                   A single-zone cluster only creates worker nodes in the same
                   zone as the cluster control-plane (specified in the 'zone'
                   argument above), whereas a multi-zone cluster can create
                   worker nodes in every zone in the same region as the
                   cluster control plane. A multi-zone cluster can help
                   job response time when a given zone becomes overburdened.
  
      Returns:
      HttpRequest on success, None otherwise
      """
  
      rz = _parse_zone(zone)
      if rz is None:
          logging.error("invalid zone specified: {}".format(zone))
          return None
  
      region, _ = rz
  
      compute_api = discovery.build(
          "compute", "v1", credentials=creds, cache_discovery=False
      )
  
      resource_limits = util.generate_resource_limits(
          compute_api, project_id, region
      )
  
      if resource_limits is None:
          logging.error("error generating resource limits")
          return None
  
      if single_zone:
          node_zones = [zone]
      else:
          node_zones = util.get_zones_in_region(
              compute_api, project_id, region
          )
  
      if node_zones is None:
          logging.error(
              "error getting zones for region {}".format(region)
          )
          return None
  
      request_body = _cluster_create_request_body(
          project_id,
          zone,
          _create_cluster_spec(
              cluster_name,
              zone,
              node_zones,
              resource_limits,
              release_channel,
          ),
      )
  
      # see https://cloud.google.com/kubernetes-engine/docs/reference/rest/v1/projects.zones.clusters/create
      return (
          cluster_api.projects()
          .zones()
          .clusters()
          .create(projectId=project_id, zone=zone, body=request_body)
      )
  
imports: import json
  import logging
  import re
  from typing import Any, Callable, Dict, Iterable, List, Optional, Tuple
  import googleapiclient
  import kubernetes
  import requests
  import urllib3
  import yaml
  from google.auth.credentials import Credentials
  from google.cloud.container_v1 import ClusterManagerClient
  from google.cloud.container_v1.types import NodePool, Cluster
  from googleapiclient import discovery
  from googleapiclient.http import HttpRequest
  from kubernetes.client import V1Container, V1DaemonSet, V1EnvVar, V1Job, V1JobSpec, V1ObjectMeta, V1Pod, V1PodSpec, V1PodTemplateSpec, V1ResourceRequirements, V1Toleration
  from kubernetes.client.api_client import ApiClient
  import caliban.config.experiment
  import caliban.platform.gke.constants
  import caliban.platform.gke.util
  from caliban.history.types import Experiment, Job, JobSpec, JobStatus, Platform
  from caliban.platform.cloud.types import GPU, TPU, Accelerator, GPUSpec, MachineType, TPUSpec
  from caliban.platform.gke.types import NodeImage, OpStatus, ReleaseChannel
  from caliban.platform.gke.util import trap
  import caliban.util.metrics
label_desc: Use image node_id 33 for calling the Cluster obj's underlying member method code with example usage: obj.create_request(cluster_api, creds, cluster_name, project_id, zone, release_channel, single_zone) and returns: cluster_api, None, None, None