code: def extract_package_dir(self):  # type: () -> Optional[str]
          
          # package_dir={'': 'lib'},
          source = self.setup_py_source()
          if not source:
              # this happens when the setup.py file is missing
              return None
  
          # sometime
          # 'package_dir'      : {'': 'src'},
          # sometimes
          # package_dir={...}
          if "package_dir=" in source:
              line = source.replace("\n", "")
              line = line.split("package_dir")[1]
              fixed = ""
              for char in line:
                  fixed += char
                  if char == "}":
                      break
              line = fixed
  
              simplified_line = line.strip(" ,").replace("'", '"')
  
              parts = simplified_line.split("=")
  
              dict_src = parts[1].strip(" \t")
              if not dict_src.endswith("}"):
                  raise JiggleVersionException(
                      "Either this is hard to parse or we have 2+ src foldrs"
                  )
              try:
                  paths_dict = ast.literal_eval(dict_src)
              except ValueError as ve:
                  logger.error(source + ": " + dict_src)
                  return ""
  
              if "" in paths_dict:
                  candidate = paths_dict[""]
                  if os.path.isdir(candidate):
                      return unicode(candidate)
              if len(paths_dict) == 1:
                  candidate = first_value_in_dict(paths_dict)
                  if os.path.isdir(candidate):
                      return unicode(candidate)
              else:
                  raise JiggleVersionException(
                      "Have path_dict, but has more than one path."
                  )
          return None
docs: Get the package_dir dictionary from source
          :return: