prompt: We are currently solving the following issue within our repository. Here is the issue text:
  --- BEGIN ISSUE ---
  Stop reading Cloud SDK's configuration to obtain the project ID
  Instead, we should subprocess out to `gcloud config config-helper --format json`
  
  Example output:
  
  ```
  {
    "configuration": {
      "active_configuration": "default",
      "properties": {
        "core": {
          "account": "[ELIDED]",
          "disable_usage_reporting": "False",
          "project": "[ELIDED]"
        }
      }
    },
    "credential": {
      "access_token": "[ELIDED]",
      "token_expiry": "2017-03-23T23:09:49Z"
    },
    "sentinels": {
      "config_sentinel": "/Users/jonwayne/.config/gcloud/config_sentinel"
    }
  }
  ```
  
  Note: we should *not* use the auth token provided here at all. We should keep our existing logic of reading `~/.config/gcloud/application_default_credentials.json` because those credentials are populated exclusively by `gcloud auth application-default login` and intended for Application Default Credentials.
  
  --- END ISSUE ---
  
  Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
  --- BEGIN FILES ---
  Path: `google/auth/_cloud_sdk.py`
  Content:
  ```
  1 # Copyright 2015 Google Inc.
  2 #
  3 # Licensed under the Apache License, Version 2.0 (the "License");
  4 # you may not use this file except in compliance with the License.
  5 # You may obtain a copy of the License at
  6 #
  7 #      http://www.apache.org/licenses/LICENSE-2.0
  8 #
  9 # Unless required by applicable law or agreed to in writing, software
  10 # distributed under the License is distributed on an "AS IS" BASIS,
  11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12 # See the License for the specific language governing permissions and
  13 # limitations under the License.
  14 
  15 """Helpers for reading the Google Cloud SDK's configuration."""
  16 
  17 import io
  18 import os
  19 
  20 import six
  21 from six.moves import configparser
  22 
  23 from google.auth import environment_vars
  24 import google.oauth2.credentials
  25 
  26 # The Google OAuth 2.0 token endpoint. Used for authorized user credentials.
  27 _GOOGLE_OAUTH2_TOKEN_ENDPOINT = 'https://accounts.google.com/o/oauth2/token'
  28 
  29 # The ~/.config subdirectory containing gcloud credentials.
  30 _CONFIG_DIRECTORY = 'gcloud'
  31 # Windows systems store config at %APPDATA%\gcloud
  32 _WINDOWS_CONFIG_ROOT_ENV_VAR = 'APPDATA'
  33 # The name of the file in the Cloud SDK config that contains default
  34 # credentials.
  35 _CREDENTIALS_FILENAME = 'application_default_credentials.json'
  36 # The config section and key for the project ID in the cloud SDK config.
  37 _PROJECT_CONFIG_SECTION = 'core'
  38 _PROJECT_CONFIG_KEY = 'project'
  39 
  40 
  41 def get_config_path():
  42     """Returns the absolute path the the Cloud SDK's configuration directory.
  43 
  44     Returns:
  45         str: The Cloud SDK config path.
  46     """
  47     # If the path is explicitly set, return that.
  48     try:
  49         return os.environ[environment_vars.CLOUD_SDK_CONFIG_DIR]
  50     except KeyError:
  51         pass
  52 
  53     # Non-windows systems store this at ~/.config/gcloud
  54     if os.name != 'nt':
  55         return os.path.join(
  56             os.path.expanduser('~'), '.config', _CONFIG_DIRECTORY)
  57     # Windows systems store config at %APPDATA%\gcloud
  58     else:
  59         try:
  60             return os.path.join(
  61                 os.environ[_WINDOWS_CONFIG_ROOT_ENV_VAR],
  62                 _CONFIG_DIRECTORY)
  63         except KeyError:
  64             # This should never happen unless someone is really
  65             # messing with things, but we'll cover the case anyway.
  66             drive = os.environ.get('SystemDrive', 'C:')
  67             return os.path.join(
  68                 drive, '\\', _CONFIG_DIRECTORY)
  69 
  70 
  71 def get_application_default_credentials_path():
  72     """Gets the path to the application default credentials file.
  73 
  74     The path may or may not exist.
  75 
  76     Returns:
  77         str: The full path to application default credentials.
  78     """
  79     config_path = get_config_path()
  80     return os.path.join(config_path, _CREDENTIALS_FILENAME)
  81 
  82 
  83 def _get_active_config(config_path):
  84     """Gets the active config for the Cloud SDK.
  85 
  86     Args:
  87         config_path (str): The Cloud SDK's config path.
  88 
  89     Returns:
  90         str: The active configuration name.
  91     """
  92     active_config_filename = os.path.join(config_path, 'active_config')
  93 
  94     if not os.path.isfile(active_config_filename):
  95         return 'default'
  96 
  97     with io.open(active_config_filename, 'r', encoding='utf-8') as file_obj:
  98         active_config_name = file_obj.read().strip()
  99 
  100     return active_config_name
  101 
  102 
  103 def _get_config_file(config_path, config_name):
  104     """Returns the full path to a configuration's config file.
  105 
  106     Args:
  107         config_path (str): The Cloud SDK's config path.
  108         config_name (str): The configuration name.
  109 
  110     Returns:
  111         str: The config file path.
  112     """
  113     return os.path.join(
  114         config_path, 'configurations', 'config_{}'.format(config_name))
  115 
  116 
  117 def get_project_id():
  118     """Gets the project ID from the Cloud SDK's configuration.
  119 
  120     Returns:
  121         Optional[str]: The project ID.
  122     """
  123     config_path = get_config_path()
  124     active_config = _get_active_config(config_path)
  125     config_file = _get_config_file(config_path, active_config)
  126 
  127     if not os.path.isfile(config_file):
  128         return None
  129 
  130     config = configparser.RawConfigParser()
  131 
  132     try:
  133         config.read(config_file)
  134 
  135         if config.has_section(_PROJECT_CONFIG_SECTION):
  136             return config.get(
  137                 _PROJECT_CONFIG_SECTION, _PROJECT_CONFIG_KEY)
  138 
  139     except configparser.Error:
  140         return None
  141 
  142 
  143 def load_authorized_user_credentials(info):
  144     """Loads an authorized user credential.
  145 
  146     Args:
  147         info (Mapping[str, str]): The loaded file's data.
  148 
  149     Returns:
  150         google.oauth2.credentials.Credentials: The constructed credentials.
  151 
  152     Raises:
  153         ValueError: if the info is in the wrong format or missing data.
  154     """
  155     keys_needed = set(('refresh_token', 'client_id', 'client_secret'))
  156     missing = keys_needed.difference(six.iterkeys(info))
  157 
  158     if missing:
  159         raise ValueError(
  160             'Authorized user info was not in the expected format, missing '
  161             'fields {}.'.format(', '.join(missing)))
  162 
  163     return google.oauth2.credentials.Credentials(
  164         None,  # No access token, must be refreshed.
  165         refresh_token=info['refresh_token'],
  166         token_uri=_GOOGLE_OAUTH2_TOKEN_ENDPOINT,
  167         client_id=info['client_id'],
  168         client_secret=info['client_secret'])
  169
  ```
  --- END FILES ---
  
  Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.
  
  Here is an example:
  
  ```diff
  diff --git a/examples/server_async.py b/examples/server_async.py
  --- a/examples/server_async.py
  +++ b/examples/server_async.py
  @@ -313,4 +313,4 @@
   
   
   if __name__ == "__main__":
  -    asyncio.run(run_async_server("."), debug=True)
  +    asyncio.run(run_async_server(), debug=True)
  diff --git a/examples/server_sync.py b/examples/server_sync.py
  --- a/examples/server_sync.py
  +++ b/examples/server_sync.py
  @@ -313,5 +313,5 @@
   
   
   if __name__ == "__main__":
  -    server = run_sync_server(".")
  +    server = run_sync_server()
       server.shutdown()
  
  ```
  
golden_diff: diff --git a/google/auth/_cloud_sdk.py b/google/auth/_cloud_sdk.py
  --- a/google/auth/_cloud_sdk.py
  +++ b/google/auth/_cloud_sdk.py
  @@ -14,11 +14,11 @@
   
   """Helpers for reading the Google Cloud SDK's configuration."""
   
  -import io
  +import json
   import os
  +import subprocess
   
   import six
  -from six.moves import configparser
   
   from google.auth import environment_vars
   import google.oauth2.credentials
  @@ -33,9 +33,9 @@
   # The name of the file in the Cloud SDK config that contains default
   # credentials.
   _CREDENTIALS_FILENAME = 'application_default_credentials.json'
  -# The config section and key for the project ID in the cloud SDK config.
  -_PROJECT_CONFIG_SECTION = 'core'
  -_PROJECT_CONFIG_KEY = 'project'
  +# The command to get the Cloud SDK configuration
  +_CLOUD_SDK_CONFIG_COMMAND = (
  +    'gcloud', 'config', 'config-helper', '--format', 'json')
   
   
   def get_config_path():
  @@ -80,66 +80,6 @@
       return os.path.join(config_path, _CREDENTIALS_FILENAME)
   
   
  -def _get_active_config(config_path):
  -    """Gets the active config for the Cloud SDK.
  -
  -    Args:
  -        config_path (str): The Cloud SDK's config path.
  -
  -    Returns:
  -        str: The active configuration name.
  -    """
  -    active_config_filename = os.path.join(config_path, 'active_config')
  -
  -    if not os.path.isfile(active_config_filename):
  -        return 'default'
  -
  -    with io.open(active_config_filename, 'r', encoding='utf-8') as file_obj:
  -        active_config_name = file_obj.read().strip()
  -
  -    return active_config_name
  -
  -
  -def _get_config_file(config_path, config_name):
  -    """Returns the full path to a configuration's config file.
  -
  -    Args:
  -        config_path (str): The Cloud SDK's config path.
  -        config_name (str): The configuration name.
  -
  -    Returns:
  -        str: The config file path.
  -    """
  -    return os.path.join(
  -        config_path, 'configurations', 'config_{}'.format(config_name))
  -
  -
  -def get_project_id():
  -    """Gets the project ID from the Cloud SDK's configuration.
  -
  -    Returns:
  -        Optional[str]: The project ID.
  -    """
  -    config_path = get_config_path()
  -    active_config = _get_active_config(config_path)
  -    config_file = _get_config_file(config_path, active_config)
  -
  -    if not os.path.isfile(config_file):
  -        return None
  -
  -    config = configparser.RawConfigParser()
  -
  -    try:
  -        config.read(config_file)
  -
  -        if config.has_section(_PROJECT_CONFIG_SECTION):
  -            return config.get(
  -                _PROJECT_CONFIG_SECTION, _PROJECT_CONFIG_KEY)
  -
  -    except configparser.Error:
  -        return None
  -
  -
   def load_authorized_user_credentials(info):
       """Loads an authorized user credential.
   
  @@ -166,3 +106,28 @@
           token_uri=_GOOGLE_OAUTH2_TOKEN_ENDPOINT,
           client_id=info['client_id'],
           client_secret=info['client_secret'])
  +
  +
  +def get_project_id():
  +    """Gets the project ID from the Cloud SDK.
  +
  +    Returns:
  +        Optional[str]: The project ID.
  +    """
  +
  +    try:
  +        output = subprocess.check_output(
  +            _CLOUD_SDK_CONFIG_COMMAND,
  +            stderr=subprocess.STDOUT)
  +    except (subprocess.CalledProcessError, OSError, IOError):
  +        return None
  +
  +    try:
  +        configuration = json.loads(output.decode('utf-8'))
  +    except ValueError:
  +        return None
  +
  +    try:
  +        return configuration['configuration']['properties']['core']['project']
  +    except KeyError:
  +        return None
  
verification_info: {"golden_diff": "diff --git a/google/auth/_cloud_sdk.py b/google/auth/_cloud_sdk.py\n--- a/google/auth/_cloud_sdk.py\n+++ b/google/auth/_cloud_sdk.py\n@@ -14,11 +14,11 @@\n \n \"\"\"Helpers for reading the Google Cloud SDK's configuration.\"\"\"\n \n-import io\n+import json\n import os\n+import subprocess\n \n import six\n-from six.moves import configparser\n \n from google.auth import environment_vars\n import google.oauth2.credentials\n@@ -33,9 +33,9 @@\n # The name of the file in the Cloud SDK config that contains default\n # credentials.\n _CREDENTIALS_FILENAME = 'application_default_credentials.json'\n-# The config section and key for the project ID in the cloud SDK config.\n-_PROJECT_CONFIG_SECTION = 'core'\n-_PROJECT_CONFIG_KEY = 'project'\n+# The command to get the Cloud SDK configuration\n+_CLOUD_SDK_CONFIG_COMMAND = (\n+    'gcloud', 'config', 'config-helper', '--format', 'json')\n \n \n def get_config_path():\n@@ -80,66 +80,6 @@\n     return os.path.join(config_path, _CREDENTIALS_FILENAME)\n \n \n-def _get_active_config(config_path):\n-    \"\"\"Gets the active config for the Cloud SDK.\n-\n-    Args:\n-        config_path (str): The Cloud SDK's config path.\n-\n-    Returns:\n-        str: The active configuration name.\n-    \"\"\"\n-    active_config_filename = os.path.join(config_path, 'active_config')\n-\n-    if not os.path.isfile(active_config_filename):\n-        return 'default'\n-\n-    with io.open(active_config_filename, 'r', encoding='utf-8') as file_obj:\n-        active_config_name = file_obj.read().strip()\n-\n-    return active_config_name\n-\n-\n-def _get_config_file(config_path, config_name):\n-    \"\"\"Returns the full path to a configuration's config file.\n-\n-    Args:\n-        config_path (str): The Cloud SDK's config path.\n-        config_name (str): The configuration name.\n-\n-    Returns:\n-        str: The config file path.\n-    \"\"\"\n-    return os.path.join(\n-        config_path, 'configurations', 'config_{}'.format(config_name))\n-\n-\n-def get_project_id():\n-    \"\"\"Gets the project ID from the Cloud SDK's configuration.\n-\n-    Returns:\n-        Optional[str]: The project ID.\n-    \"\"\"\n-    config_path = get_config_path()\n-    active_config = _get_active_config(config_path)\n-    config_file = _get_config_file(config_path, active_config)\n-\n-    if not os.path.isfile(config_file):\n-        return None\n-\n-    config = configparser.RawConfigParser()\n-\n-    try:\n-        config.read(config_file)\n-\n-        if config.has_section(_PROJECT_CONFIG_SECTION):\n-            return config.get(\n-                _PROJECT_CONFIG_SECTION, _PROJECT_CONFIG_KEY)\n-\n-    except configparser.Error:\n-        return None\n-\n-\n def load_authorized_user_credentials(info):\n     \"\"\"Loads an authorized user credential.\n \n@@ -166,3 +106,28 @@\n         token_uri=_GOOGLE_OAUTH2_TOKEN_ENDPOINT,\n         client_id=info['client_id'],\n         client_secret=info['client_secret'])\n+\n+\n+def get_project_id():\n+    \"\"\"Gets the project ID from the Cloud SDK.\n+\n+    Returns:\n+        Optional[str]: The project ID.\n+    \"\"\"\n+\n+    try:\n+        output = subprocess.check_output(\n+            _CLOUD_SDK_CONFIG_COMMAND,\n+            stderr=subprocess.STDOUT)\n+    except (subprocess.CalledProcessError, OSError, IOError):\n+        return None\n+\n+    try:\n+        configuration = json.loads(output.decode('utf-8'))\n+    except ValueError:\n+        return None\n+\n+    try:\n+        return configuration['configuration']['properties']['core']['project']\n+    except KeyError:\n+        return None\n", "issue": "Stop reading Cloud SDK's configuration to obtain the project ID\nInstead, we should subprocess out to `gcloud config config-helper --format json`\r\n\r\nExample output:\r\n\r\n```\r\n{\r\n  \"configuration\": {\r\n    \"active_configuration\": \"default\",\r\n    \"properties\": {\r\n      \"core\": {\r\n        \"account\": \"[ELIDED]\",\r\n        \"disable_usage_reporting\": \"False\",\r\n        \"project\": \"[ELIDED]\"\r\n      }\r\n    }\r\n  },\r\n  \"credential\": {\r\n    \"access_token\": \"[ELIDED]\",\r\n    \"token_expiry\": \"2017-03-23T23:09:49Z\"\r\n  },\r\n  \"sentinels\": {\r\n    \"config_sentinel\": \"/Users/jonwayne/.config/gcloud/config_sentinel\"\r\n  }\r\n}\r\n```\r\n\r\nNote: we should *not* use the auth token provided here at all. We should keep our existing logic of reading `~/.config/gcloud/application_default_credentials.json` because those credentials are populated exclusively by `gcloud auth application-default login` and intended for Application Default Credentials.\n", "before_files": [{"content": "# Copyright 2015 Google Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#      http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Helpers for reading the Google Cloud SDK's configuration.\"\"\"\n\nimport io\nimport os\n\nimport six\nfrom six.moves import configparser\n\nfrom google.auth import environment_vars\nimport google.oauth2.credentials\n\n# The Google OAuth 2.0 token endpoint. Used for authorized user credentials.\n_GOOGLE_OAUTH2_TOKEN_ENDPOINT = 'https://accounts.google.com/o/oauth2/token'\n\n# The ~/.config subdirectory containing gcloud credentials.\n_CONFIG_DIRECTORY = 'gcloud'\n# Windows systems store config at %APPDATA%\\gcloud\n_WINDOWS_CONFIG_ROOT_ENV_VAR = 'APPDATA'\n# The name of the file in the Cloud SDK config that contains default\n# credentials.\n_CREDENTIALS_FILENAME = 'application_default_credentials.json'\n# The config section and key for the project ID in the cloud SDK config.\n_PROJECT_CONFIG_SECTION = 'core'\n_PROJECT_CONFIG_KEY = 'project'\n\n\ndef get_config_path():\n    \"\"\"Returns the absolute path the the Cloud SDK's configuration directory.\n\n    Returns:\n        str: The Cloud SDK config path.\n    \"\"\"\n    # If the path is explicitly set, return that.\n    try:\n        return os.environ[environment_vars.CLOUD_SDK_CONFIG_DIR]\n    except KeyError:\n        pass\n\n    # Non-windows systems store this at ~/.config/gcloud\n    if os.name != 'nt':\n        return os.path.join(\n            os.path.expanduser('~'), '.config', _CONFIG_DIRECTORY)\n    # Windows systems store config at %APPDATA%\\gcloud\n    else:\n        try:\n            return os.path.join(\n                os.environ[_WINDOWS_CONFIG_ROOT_ENV_VAR],\n                _CONFIG_DIRECTORY)\n        except KeyError:\n            # This should never happen unless someone is really\n            # messing with things, but we'll cover the case anyway.\n            drive = os.environ.get('SystemDrive', 'C:')\n            return os.path.join(\n                drive, '\\\\', _CONFIG_DIRECTORY)\n\n\ndef get_application_default_credentials_path():\n    \"\"\"Gets the path to the application default credentials file.\n\n    The path may or may not exist.\n\n    Returns:\n        str: The full path to application default credentials.\n    \"\"\"\n    config_path = get_config_path()\n    return os.path.join(config_path, _CREDENTIALS_FILENAME)\n\n\ndef _get_active_config(config_path):\n    \"\"\"Gets the active config for the Cloud SDK.\n\n    Args:\n        config_path (str): The Cloud SDK's config path.\n\n    Returns:\n        str: The active configuration name.\n    \"\"\"\n    active_config_filename = os.path.join(config_path, 'active_config')\n\n    if not os.path.isfile(active_config_filename):\n        return 'default'\n\n    with io.open(active_config_filename, 'r', encoding='utf-8') as file_obj:\n        active_config_name = file_obj.read().strip()\n\n    return active_config_name\n\n\ndef _get_config_file(config_path, config_name):\n    \"\"\"Returns the full path to a configuration's config file.\n\n    Args:\n        config_path (str): The Cloud SDK's config path.\n        config_name (str): The configuration name.\n\n    Returns:\n        str: The config file path.\n    \"\"\"\n    return os.path.join(\n        config_path, 'configurations', 'config_{}'.format(config_name))\n\n\ndef get_project_id():\n    \"\"\"Gets the project ID from the Cloud SDK's configuration.\n\n    Returns:\n        Optional[str]: The project ID.\n    \"\"\"\n    config_path = get_config_path()\n    active_config = _get_active_config(config_path)\n    config_file = _get_config_file(config_path, active_config)\n\n    if not os.path.isfile(config_file):\n        return None\n\n    config = configparser.RawConfigParser()\n\n    try:\n        config.read(config_file)\n\n        if config.has_section(_PROJECT_CONFIG_SECTION):\n            return config.get(\n                _PROJECT_CONFIG_SECTION, _PROJECT_CONFIG_KEY)\n\n    except configparser.Error:\n        return None\n\n\ndef load_authorized_user_credentials(info):\n    \"\"\"Loads an authorized user credential.\n\n    Args:\n        info (Mapping[str, str]): The loaded file's data.\n\n    Returns:\n        google.oauth2.credentials.Credentials: The constructed credentials.\n\n    Raises:\n        ValueError: if the info is in the wrong format or missing data.\n    \"\"\"\n    keys_needed = set(('refresh_token', 'client_id', 'client_secret'))\n    missing = keys_needed.difference(six.iterkeys(info))\n\n    if missing:\n        raise ValueError(\n            'Authorized user info was not in the expected format, missing '\n            'fields {}.'.format(', '.join(missing)))\n\n    return google.oauth2.credentials.Credentials(\n        None,  # No access token, must be refreshed.\n        refresh_token=info['refresh_token'],\n        token_uri=_GOOGLE_OAUTH2_TOKEN_ENDPOINT,\n        client_id=info['client_id'],\n        client_secret=info['client_secret'])\n", "path": "google/auth/_cloud_sdk.py"}], "after_files": [{"content": "# Copyright 2015 Google Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#      http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Helpers for reading the Google Cloud SDK's configuration.\"\"\"\n\nimport json\nimport os\nimport subprocess\n\nimport six\n\nfrom google.auth import environment_vars\nimport google.oauth2.credentials\n\n# The Google OAuth 2.0 token endpoint. Used for authorized user credentials.\n_GOOGLE_OAUTH2_TOKEN_ENDPOINT = 'https://accounts.google.com/o/oauth2/token'\n\n# The ~/.config subdirectory containing gcloud credentials.\n_CONFIG_DIRECTORY = 'gcloud'\n# Windows systems store config at %APPDATA%\\gcloud\n_WINDOWS_CONFIG_ROOT_ENV_VAR = 'APPDATA'\n# The name of the file in the Cloud SDK config that contains default\n# credentials.\n_CREDENTIALS_FILENAME = 'application_default_credentials.json'\n# The command to get the Cloud SDK configuration\n_CLOUD_SDK_CONFIG_COMMAND = (\n    'gcloud', 'config', 'config-helper', '--format', 'json')\n\n\ndef get_config_path():\n    \"\"\"Returns the absolute path the the Cloud SDK's configuration directory.\n\n    Returns:\n        str: The Cloud SDK config path.\n    \"\"\"\n    # If the path is explicitly set, return that.\n    try:\n        return os.environ[environment_vars.CLOUD_SDK_CONFIG_DIR]\n    except KeyError:\n        pass\n\n    # Non-windows systems store this at ~/.config/gcloud\n    if os.name != 'nt':\n        return os.path.join(\n            os.path.expanduser('~'), '.config', _CONFIG_DIRECTORY)\n    # Windows systems store config at %APPDATA%\\gcloud\n    else:\n        try:\n            return os.path.join(\n                os.environ[_WINDOWS_CONFIG_ROOT_ENV_VAR],\n                _CONFIG_DIRECTORY)\n        except KeyError:\n            # This should never happen unless someone is really\n            # messing with things, but we'll cover the case anyway.\n            drive = os.environ.get('SystemDrive', 'C:')\n            return os.path.join(\n                drive, '\\\\', _CONFIG_DIRECTORY)\n\n\ndef get_application_default_credentials_path():\n    \"\"\"Gets the path to the application default credentials file.\n\n    The path may or may not exist.\n\n    Returns:\n        str: The full path to application default credentials.\n    \"\"\"\n    config_path = get_config_path()\n    return os.path.join(config_path, _CREDENTIALS_FILENAME)\n\n\ndef load_authorized_user_credentials(info):\n    \"\"\"Loads an authorized user credential.\n\n    Args:\n        info (Mapping[str, str]): The loaded file's data.\n\n    Returns:\n        google.oauth2.credentials.Credentials: The constructed credentials.\n\n    Raises:\n        ValueError: if the info is in the wrong format or missing data.\n    \"\"\"\n    keys_needed = set(('refresh_token', 'client_id', 'client_secret'))\n    missing = keys_needed.difference(six.iterkeys(info))\n\n    if missing:\n        raise ValueError(\n            'Authorized user info was not in the expected format, missing '\n            'fields {}.'.format(', '.join(missing)))\n\n    return google.oauth2.credentials.Credentials(\n        None,  # No access token, must be refreshed.\n        refresh_token=info['refresh_token'],\n        token_uri=_GOOGLE_OAUTH2_TOKEN_ENDPOINT,\n        client_id=info['client_id'],\n        client_secret=info['client_secret'])\n\n\ndef get_project_id():\n    \"\"\"Gets the project ID from the Cloud SDK.\n\n    Returns:\n        Optional[str]: The project ID.\n    \"\"\"\n\n    try:\n        output = subprocess.check_output(\n            _CLOUD_SDK_CONFIG_COMMAND,\n            stderr=subprocess.STDOUT)\n    except (subprocess.CalledProcessError, OSError, IOError):\n        return None\n\n    try:\n        configuration = json.loads(output.decode('utf-8'))\n    except ValueError:\n        return None\n\n    try:\n        return configuration['configuration']['properties']['core']['project']\n    except KeyError:\n        return None\n", "path": "google/auth/_cloud_sdk.py"}]}