code: def completion(
      self,
      model_response: ModelResponse,
      api_key: str,
      model: str,
      messages: list,
      timeout: float,
      print_verbose: Optional[Callable] = None,
      api_base: Optional[str] = None,
      logging_obj=None,
      acompletion: bool = False,
      optional_params=None,
      litellm_params=None,
      logger_fn=None,
      headers: Optional[dict] = None,
  ):
      super().completion()
      exception_mapping_worked = False
      try:
          if headers is None:
              headers = self.validate_environment(api_key=api_key)
          if model is None or messages is None:
              raise OpenAIError(
                  status_code=422, message=f"Missing model or messages"
              )
  
          api_base = f"{api_base}/completions"
  
          if (
              len(messages) > 0
              and "content" in messages[0]
              and type(messages[0]["content"]) == list
          ):
              prompt = messages[0]["content"]
          else:
              prompt = " ".join([message["content"] for message in messages])  # type: ignore
  
          # don't send max retries to the api, if set
          optional_params.pop("max_retries", None)
  
          data = {"model": model, "prompt": prompt, **optional_params}
          ## LOGGING
          logging_obj.pre_call(
              input=messages,
              api_key=api_key,
              additional_args={
                  "headers": headers,
                  "api_base": api_base,
                  "complete_input_dict": data,
              },
          )
          if acompletion == True:
              if optional_params.get("stream", False):
                  return self.async_streaming(
                      logging_obj=logging_obj,
                      api_base=api_base,
                      data=data,
                      headers=headers,
                      model_response=model_response,
                      model=model,
                      timeout=timeout,
                  )
              else:
                  return self.acompletion(api_base=api_base, data=data, headers=headers, model_response=model_response, prompt=prompt, api_key=api_key, logging_obj=logging_obj, model=model, timeout=timeout)  # type: ignore
          elif optional_params.get("stream", False):
              return self.streaming(
                  logging_obj=logging_obj,
                  api_base=api_base,
                  data=data,
                  headers=headers,
                  model_response=model_response,
                  model=model,
                  timeout=timeout,
              )
          else:
              response = httpx.post(
                  url=f"{api_base}",
                  json=data,
                  headers=headers,
                  timeout=timeout,
              )
              if response.status_code != 200:
                  raise OpenAIError(
                      status_code=response.status_code,
                      message=response.text,
                  )
  
              ## LOGGING
              logging_obj.post_call(
                  input=prompt,
                  api_key=api_key,
                  original_response=response,
                  additional_args={
                      "headers": headers,
                      "api_base": api_base,
                  },
              )
  
              ## RESPONSE OBJECT
              return self.convert_to_model_response_object(
                  response_object=response.json(),
                  model_response_object=model_response,
              )
      except Exception as e:
          raise e
  
imports: from typing import Optional, Union, Any
  import types, time, json
  import httpx
  from .base import BaseLLM
  from litellm.utils import ModelResponse, Choices, Message, CustomStreamWrapper, convert_to_model_response_object, Usage
  from typing import Callable, Optional
  import aiohttp, requests
  import litellm
  from .prompt_templates.factory import prompt_factory, custom_prompt
  from openai import OpenAI, AsyncOpenAI
label_desc: Use image node_id 4 for calling the OpenAITextCompletion obj's underlying member method code with example usage: obj.completion(model_response, api_key, model, messages, timeout, print_verbose, api_base, logging_obj, acompletion, optional_params, litellm_params, logger_fn, headers) and returns: self, self, self, self