class_docstr: Method of encapsulating utility files 
class_docstr_tok: ["Method","of","encapsulating","utility","files"]
code: def wait_for_bulk_insert_tasks_completed(
      self,
      task_ids,
      target_state=BulkInsertState.ImportCompleted,
      timeout=None,
      using="default",
      **kwargs,
  ):
      tasks_state_distribution = {
          "success": set(),
          "failed": set(),
          "in_progress": set(),
      }
      tasks_state = {}
      if timeout is not None:
          task_timeout = timeout
      else:
          task_timeout = TIMEOUT
      start = time.time()
      end = time.time()
      log.info(f"wait bulk load timeout is {task_timeout}")
      pending_tasks = self.get_bulk_insert_pending_list()
      log.info(
          f"before waiting, there are {len(pending_tasks)} pending tasks"
      )
      while (
          len(tasks_state_distribution["success"])
          + len(tasks_state_distribution["failed"])
          < len(task_ids)
          and end - start <= task_timeout
      ):
          time.sleep(2)
  
          for task_id in task_ids:
              if (
                  task_id in tasks_state_distribution["success"]
                  or task_id in tasks_state_distribution["failed"]
              ):
                  continue
              else:
                  state, _ = self.get_bulk_insert_state(
                      task_id, task_timeout, using, **kwargs
                  )
                  tasks_state[task_id] = state
  
                  if target_state == BulkInsertState.ImportPersisted:
                      if state.state in [
                          BulkInsertState.ImportPersisted,
                          BulkInsertState.ImportCompleted,
                      ]:
                          if (
                              task_id
                              in tasks_state_distribution["in_progress"]
                          ):
                              tasks_state_distribution[
                                  "in_progress"
                              ].remove(task_id)
                          tasks_state_distribution["success"].add(
                              task_id
                          )
                      elif state.state in [
                          BulkInsertState.ImportPending,
                          BulkInsertState.ImportStarted,
                      ]:
                          tasks_state_distribution["in_progress"].add(
                              task_id
                          )
                      else:
                          tasks_state_distribution["failed"].add(
                              task_id
                          )
  
                  if target_state == BulkInsertState.ImportCompleted:
                      if state.state in [
                          BulkInsertState.ImportCompleted
                      ]:
                          if (
                              task_id
                              in tasks_state_distribution["in_progress"]
                          ):
                              tasks_state_distribution[
                                  "in_progress"
                              ].remove(task_id)
                          tasks_state_distribution["success"].add(
                              task_id
                          )
                      elif state.state in [
                          BulkInsertState.ImportPending,
                          BulkInsertState.ImportStarted,
                          BulkInsertState.ImportPersisted,
                      ]:
                          tasks_state_distribution["in_progress"].add(
                              task_id
                          )
                      else:
                          tasks_state_distribution["failed"].add(
                              task_id
                          )
  
          end = time.time()
      pending_tasks = self.get_bulk_insert_pending_list()
      log.info(
          f"after waiting, there are {len(pending_tasks)} pending tasks"
      )
      log.info(f"task state distribution: {tasks_state_distribution}")
      log.info(tasks_state)
      if len(tasks_state_distribution["success"]) == len(task_ids):
          log.info(
              f"wait for bulk load tasks completed successfully, cost time: {end - start}"
          )
          return True, tasks_state
      else:
          log.info(
              f"wait for bulk load tasks completed failed, cost time: {end - start}"
          )
          return False, tasks_state
  
imports: from datetime import datetime
  import time
  from pymilvus import utility
  import sys
  from check.func_check import ResponseChecker
  from utils.api_request import api_request
  from pymilvus import BulkInsertState
  from pymilvus.orm.role import Role
  from utils.util_log import test_log
label_desc: Use image node_id 7 for calling the ApiUtilityWrapper obj's underlying member method code with example usage: obj.wait_for_bulk_insert_tasks_completed(task_ids, target_state, timeout, using) and returns: True,  tasks_state, False,  tasks_state