# Copyright 2020 The Pigweed Authors
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may not
# use this file except in compliance with the License. You may obtain a copy of
# the License at
#
#     https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations under
# the License.
"""The env module defines the environment variables used by Pigweed."""

from typing import Optional

from pw_cli import envparse


def pigweed_environment_parser() -> envparse.EnvironmentParser:
    """Defines Pigweed's environment variables on an EnvironmentParser."""
    parser = envparse.EnvironmentParser(prefix='PW_')

    parser.add_var('PW_BOOTSTRAP_PYTHON')
    parser.add_var('PW_ENABLE_PRESUBMIT_HOOK_WARNING', default=False)
    parser.add_var('PW_EMOJI', type=envparse.strict_bool, default=False)
    parser.add_var('PW_ENVSETUP')
    parser.add_var('PW_ENVSETUP_FULL')
    parser.add_var('PW_ENVSETUP_NO_BANNER',
                   type=envparse.strict_bool,
                   default=False)
    parser.add_var('PW_ENVSETUP_QUIET',
                   type=envparse.strict_bool,
                   default=False)
    parser.add_var('PW_ENVIRONMENT_ROOT')
    parser.add_var('PW_PACKAGE_ROOT')
    parser.add_var('PW_PROJECT_ROOT')
    parser.add_var('PW_ROOT')
    parser.add_var('PW_SKIP_BOOTSTRAP')
    parser.add_var('PW_SUBPROCESS', type=envparse.strict_bool, default=False)
    parser.add_var('PW_USE_COLOR', type=envparse.strict_bool, default=False)
    parser.add_var('PW_USE_GCS_ENVSETUP', type=envparse.strict_bool)

    parser.add_allowed_suffix('_CIPD_INSTALL_DIR')

    parser.add_var('PW_ENVSETUP_DISABLE_SPINNER',
                   type=envparse.strict_bool,
                   default=False)
    parser.add_var('PW_DOCTOR_SKIP_CIPD_CHECKS')
    parser.add_var('PW_ACTIVATE_SKIP_CHECKS',
                   type=envparse.strict_bool,
                   default=False)

    parser.add_var('PW_BANNER_FUNC')
    parser.add_var('PW_BRANDING_BANNER')
    parser.add_var('PW_BRANDING_BANNER_COLOR', default='magenta')

    parser.add_var('PW_PRESUBMIT_DISABLE_SUBPROCESS_CAPTURE',
                   type=envparse.strict_bool)

    parser.add_var('PW_CONSOLE_CONFIG_FILE')
    parser.add_var('PW_ENVIRONMENT_NO_ERROR_ON_UNRECOGNIZED')

    # RBE environment variables
    parser.add_var('PW_USE_RBE', default=False)
    parser.add_var('PW_RBE_DEBUG', default=False)
    parser.add_var('PW_RBE_CLANG_CONFIG', default='')
    parser.add_var('PW_RBE_ARM_GCC_CONFIG', default='')

    return parser


# Internal: memoize environment parsing to avoid unnecessary computation in
# multiple calls to pigweed_environment().
_memoized_environment: Optional[envparse.EnvNamespace] = None


def pigweed_environment() -> envparse.EnvNamespace:
    """Returns Pigweed's parsed environment."""
    global _memoized_environment  # pylint: disable=global-statement

    if _memoized_environment is None:
        _memoized_environment = pigweed_environment_parser().parse_env()

    return _memoized_environment
