diff --git a/CIME/XML/archive_base.py b/CIME/XML/archive_base.py index ff8c096ce9f..4a7933614a4 100644 --- a/CIME/XML/archive_base.py +++ b/CIME/XML/archive_base.py @@ -1,6 +1,7 @@ """ Base class for archive files. This class inherits from generic_xml.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.utils import convert_to_type diff --git a/CIME/XML/batch.py b/CIME/XML/batch.py index 75d9b1cfb94..84b9b24fd1a 100644 --- a/CIME/XML/batch.py +++ b/CIME/XML/batch.py @@ -4,10 +4,11 @@ The batch_system type="foo" blocks define most things. Machine-specific overrides can be defined by providing a batch_system MACH="mach" block. """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.XML.files import Files -from CIME.utils import expect +from CIME.utils import expect, get_config_dir logger = logging.getLogger(__name__) @@ -45,13 +46,15 @@ def __init__( self.batch_system = batch_system self.machine = machine - # Append the contents of $HOME/.cime/config_batch.xml if it exists. + # Append the contents of $HOME/get_config_dir()/config_batch.xml if it exists. # # Also append the contents of a config_batch.xml file in the directory given by # extra_machines_dir, if present. # # This could cause problems if node matches are repeated when only one is expected. - infile = os.path.join(os.environ.get("HOME"), ".cime", "config_batch.xml") + infile = os.path.join( + os.environ.get("HOME"), get_config_dir(), "config_batch.xml" + ) usehome = False if os.path.exists(infile): GenericXML.read(self, infile) diff --git a/CIME/XML/component.py b/CIME/XML/component.py index abd09c86fd0..51375c21301 100644 --- a/CIME/XML/component.py +++ b/CIME/XML/component.py @@ -1,6 +1,7 @@ """ Interface to the config_component.xml files. This class inherits from EntryID.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.entry_id import EntryID diff --git a/CIME/XML/entry_id.py b/CIME/XML/entry_id.py index c090a3633db..a8a9c3f24c0 100644 --- a/CIME/XML/entry_id.py +++ b/CIME/XML/entry_id.py @@ -3,6 +3,7 @@ this is an abstract class and is expected to be used by other XML interface modules and not directly. """ + from CIME.XML.standard_module_setup import * from CIME.utils import expect, convert_to_string, convert_to_type from CIME.XML.generic_xml import GenericXML diff --git a/CIME/XML/env_archive.py b/CIME/XML/env_archive.py index 3642cda40a8..57b2b15723c 100644 --- a/CIME/XML/env_archive.py +++ b/CIME/XML/env_archive.py @@ -1,12 +1,15 @@ """ Interface to the env_archive.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME import utils from CIME.XML.archive_base import ArchiveBase from CIME.XML.env_base import EnvBase logger = logging.getLogger(__name__) + + # pylint: disable=super-init-not-called class EnvArchive(ArchiveBase, EnvBase): def __init__(self, case_root=None, infile="env_archive.xml", read_only=False): diff --git a/CIME/XML/env_base.py b/CIME/XML/env_base.py index b30d33da988..372259d7d71 100644 --- a/CIME/XML/env_base.py +++ b/CIME/XML/env_base.py @@ -1,6 +1,7 @@ """ Base class for env files. This class inherits from EntryID.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.entry_id import EntryID from CIME.XML.headers import Headers diff --git a/CIME/XML/env_batch.py b/CIME/XML/env_batch.py index 9bc4034a41a..096e784478b 100644 --- a/CIME/XML/env_batch.py +++ b/CIME/XML/env_batch.py @@ -16,6 +16,7 @@ get_logging_options, format_time, add_flag_to_cmd, + get_config_dir, ) from collections import OrderedDict import stat, re, math @@ -632,7 +633,7 @@ def _get_arg_nodes(self, case, bs_nodes): check_paths = [case.get_value("BATCH_SPEC_FILE")] user_config_path = os.path.join( - pathlib.Path().home(), ".cime", "config_batch.xml" + pathlib.Path().home(), get_config_dir(), "config_batch.xml" ) if os.path.exists(user_config_path): diff --git a/CIME/XML/env_build.py b/CIME/XML/env_build.py index fe863e414ef..f9c05486baa 100644 --- a/CIME/XML/env_build.py +++ b/CIME/XML/env_build.py @@ -1,6 +1,7 @@ """ Interface to the env_build.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME import utils diff --git a/CIME/XML/env_case.py b/CIME/XML/env_case.py index 1b4c85d6f88..9e002fa18ef 100644 --- a/CIME/XML/env_case.py +++ b/CIME/XML/env_case.py @@ -1,6 +1,7 @@ """ Interface to the env_case.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME import utils diff --git a/CIME/XML/env_mach_pes.py b/CIME/XML/env_mach_pes.py index 3dba2c95ecb..75f3bff9afd 100644 --- a/CIME/XML/env_mach_pes.py +++ b/CIME/XML/env_mach_pes.py @@ -1,6 +1,7 @@ """ Interface to the env_mach_pes.xml file. This class inherits from EntryID """ + from CIME.XML.standard_module_setup import * from CIME import utils from CIME.XML.env_base import EnvBase diff --git a/CIME/XML/env_mach_specific.py b/CIME/XML/env_mach_specific.py index e94d367e66c..526419334fc 100644 --- a/CIME/XML/env_mach_specific.py +++ b/CIME/XML/env_mach_specific.py @@ -1,6 +1,7 @@ """ Interface to the env_mach_specific.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME.XML.env_base import EnvBase @@ -11,6 +12,7 @@ logger = logging.getLogger(__name__) + # Is not of type EntryID but can use functions from EntryID (e.g # get_type) otherwise need to implement own functions and make GenericXML parent class class EnvMachSpecific(EnvBase): diff --git a/CIME/XML/env_postprocessing.py b/CIME/XML/env_postprocessing.py index 90f56f24d64..62e8f973664 100644 --- a/CIME/XML/env_postprocessing.py +++ b/CIME/XML/env_postprocessing.py @@ -1,6 +1,7 @@ """ Interface to the env_postprocessing.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME.XML.env_base import EnvBase diff --git a/CIME/XML/env_run.py b/CIME/XML/env_run.py index 2e34c86c8f7..d95ef8acd61 100644 --- a/CIME/XML/env_run.py +++ b/CIME/XML/env_run.py @@ -1,6 +1,7 @@ """ Interface to the env_run.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME.XML.env_base import EnvBase diff --git a/CIME/XML/env_test.py b/CIME/XML/env_test.py index 9dbe3615eff..54513ac7659 100644 --- a/CIME/XML/env_test.py +++ b/CIME/XML/env_test.py @@ -1,6 +1,7 @@ """ Interface to the env_test.xml file. This class inherits from EnvBase """ + from CIME.XML.standard_module_setup import * from CIME.XML.env_base import EnvBase diff --git a/CIME/XML/generic_xml.py b/CIME/XML/generic_xml.py index d35815d7829..5f599c3edc1 100644 --- a/CIME/XML/generic_xml.py +++ b/CIME/XML/generic_xml.py @@ -2,6 +2,7 @@ Common interface to XML files, this is an abstract class and is expected to be used by other XML interface modules and not directly. """ + from CIME.XML.standard_module_setup import * from CIME.utils import safe_copy, get_src_root @@ -399,10 +400,12 @@ def get_child(self, name=None, attributes=None, root=None, err_msg=None): ) expect( child, - err_msg - if err_msg - else "Expected one child, found None with name '{}' and attribs '{}' in file {}".format( - name, attributes, self.filename + ( + err_msg + if err_msg + else "Expected one child, found None with name '{}' and attribs '{}' in file {}".format( + name, attributes, self.filename + ) ), ) return child @@ -419,10 +422,12 @@ def get_optional_child(self, name=None, attributes=None, root=None, err_msg=None expect( len(children) <= 1, - err_msg - if err_msg - else "Multiple matches for name '{}' and attribs '{}' in file {}".format( - name, attributes, self.filename + ( + err_msg + if err_msg + else "Multiple matches for name '{}' and attribs '{}' in file {}".format( + name, attributes, self.filename + ) ), ) return children[0] if children else None diff --git a/CIME/XML/headers.py b/CIME/XML/headers.py index 5937a1d03cb..b7fe64c5de9 100644 --- a/CIME/XML/headers.py +++ b/CIME/XML/headers.py @@ -1,6 +1,7 @@ """ Interface to the config_headers.xml file. This class inherits from EntryID.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML diff --git a/CIME/XML/inputdata.py b/CIME/XML/inputdata.py index 18b71dca4dd..4599315536e 100644 --- a/CIME/XML/inputdata.py +++ b/CIME/XML/inputdata.py @@ -1,6 +1,7 @@ """ Interface to the config_inputdata.xml file. This class inherits from GenericXML.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.XML.files import Files diff --git a/CIME/XML/machines.py b/CIME/XML/machines.py index c40e73ba3b6..dd6a27dd809 100644 --- a/CIME/XML/machines.py +++ b/CIME/XML/machines.py @@ -5,7 +5,13 @@ from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.XML.files import Files -from CIME.utils import CIMEError, expect, convert_to_unknown_type, get_cime_config +from CIME.utils import ( + CIMEError, + expect, + convert_to_unknown_type, + get_cime_config, + get_config_dir, +) import re import logging @@ -99,14 +105,14 @@ def __init__( GenericXML.__init__(self, infile, schema, read_only=read_only) - # Append the contents of $HOME/.cime/config_machines.xml if it exists. + # Append the contents of $HOME/get_config_dir()/config_machines.xml if it exists. # # Also append the contents of a config_machines.xml file in the directory given by # extra_machines_dir, if present. # # This could cause problems if node matches are repeated when only one is expected. local_infile = os.path.join( - os.environ.get("HOME"), ".cime", "config_machines.xml" + os.environ.get("HOME"), get_config_dir(), "config_machines.xml" ) logger.debug("Infile: {}".format(local_infile)) @@ -349,7 +355,9 @@ def set_machine(self, machine, schema=None): if machine == "Query": return machine elif self.get_version() == 3: - machines_file = Path.home() / ".cime" / machine / "config_machines.xml" + machines_file = ( + Path.home() / get_config_dir() / machine / "config_machines.xml" + ) if machines_file.exists(): GenericXML.read( diff --git a/CIME/XML/namelist_definition.py b/CIME/XML/namelist_definition.py index 7ca7c477009..a1698b78ffe 100644 --- a/CIME/XML/namelist_definition.py +++ b/CIME/XML/namelist_definition.py @@ -32,7 +32,6 @@ class CaseInsensitiveDict(dict): - """Basic case insensitive dict with strings only keys. From https://stackoverflow.com/a/27890005""" @@ -65,7 +64,6 @@ def __setitem__(self, k, v): class NamelistDefinition(EntryID): - """Class representing variable definitions for a namelist. This class inherits from `EntryID`, and supports most inherited methods; however, `set_value` is unsupported. diff --git a/CIME/XML/pes.py b/CIME/XML/pes.py index 3254751c794..fa1389919d5 100644 --- a/CIME/XML/pes.py +++ b/CIME/XML/pes.py @@ -1,6 +1,7 @@ """ Interface to the config_pes.xml file. This class inherits from GenericXML.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.XML.files import Files diff --git a/CIME/XML/pio.py b/CIME/XML/pio.py index 54af6112bf0..59f705696c6 100644 --- a/CIME/XML/pio.py +++ b/CIME/XML/pio.py @@ -1,6 +1,7 @@ """ Class for config_pio files . This class inherits from EntryID.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.entry_id import EntryID from CIME.XML.files import Files diff --git a/CIME/XML/postprocessing.py b/CIME/XML/postprocessing.py index 3287d145142..510c5f676a1 100644 --- a/CIME/XML/postprocessing.py +++ b/CIME/XML/postprocessing.py @@ -5,7 +5,7 @@ from CIME.XML.standard_module_setup import * from CIME.XML.entry_id import EntryID from CIME.XML.files import Files -from CIME.utils import expect +from CIME.utils import expect, get_config_dir logger = logging.getLogger(__name__) @@ -31,10 +31,10 @@ def __init__(self, infile=None, files=None): EntryID.__init__(self, infile, schema=schema) - # Append the contents of $HOME/.cime/config_postprocessing.xml if it exists + # Append the contents of $HOME/get_config_dir()/config_postprocessing.xml if it exists # This could cause problems if node matchs are repeated when only one is expected infile = os.path.join( - os.environ.get("HOME"), ".cime", "config_postprocessing.xml" + os.environ.get("HOME"), get_config_dir(), "config_postprocessing.xml" ) if os.path.exists(infile): EntryID.read(self, infile) diff --git a/CIME/XML/stream.py b/CIME/XML/stream.py index 95dfa30ef7d..f571ac3ab5b 100644 --- a/CIME/XML/stream.py +++ b/CIME/XML/stream.py @@ -3,6 +3,7 @@ stream files predate cime and so do not conform to entry id format """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.XML.files import Files diff --git a/CIME/XML/test_reporter.py b/CIME/XML/test_reporter.py index 93f117a8a46..9509d0bb58b 100644 --- a/CIME/XML/test_reporter.py +++ b/CIME/XML/test_reporter.py @@ -2,6 +2,7 @@ Interface to the testreporter xml. This class inherits from GenericXML.py """ + # pylint: disable=import-error import urllib.parse import urllib.request diff --git a/CIME/XML/testlist.py b/CIME/XML/testlist.py index 6dbe79b8f98..58691a9b611 100644 --- a/CIME/XML/testlist.py +++ b/CIME/XML/testlist.py @@ -35,6 +35,7 @@ - workflow: adds a workflow to the test """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML diff --git a/CIME/XML/tests.py b/CIME/XML/tests.py index 4a9eefc0fc4..e367f3aa968 100644 --- a/CIME/XML/tests.py +++ b/CIME/XML/tests.py @@ -1,6 +1,7 @@ """ Interface to the config_tests.xml file. This class inherits from GenericEntry """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML diff --git a/CIME/XML/testspec.py b/CIME/XML/testspec.py index 9b4e7c37724..65b476d191f 100644 --- a/CIME/XML/testspec.py +++ b/CIME/XML/testspec.py @@ -1,6 +1,7 @@ """ Interface to the testspec.xml file. This class inherits from generic_xml.py """ + from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML diff --git a/CIME/XML/workflow.py b/CIME/XML/workflow.py index 4824e03b666..f9b3757f3fb 100644 --- a/CIME/XML/workflow.py +++ b/CIME/XML/workflow.py @@ -5,7 +5,7 @@ from CIME.XML.standard_module_setup import * from CIME.XML.generic_xml import GenericXML from CIME.XML.files import Files -from CIME.utils import expect +from CIME.utils import expect, get_config_dir logger = logging.getLogger(__name__) @@ -25,9 +25,11 @@ def __init__(self, infile=None, files=None): GenericXML.__init__(self, infile, schema=schema) - # Append the contents of $HOME/.cime/config_workflow.xml if it exists + # Append the contents of $HOME/get_config_dir()/config_workflow.xml if it exists # This could cause problems if node matchs are repeated when only one is expected - infile = os.path.join(os.environ.get("HOME"), ".cime", "config_workflow.xml") + infile = os.path.join( + os.environ.get("HOME"), get_config_dir(), "config_workflow.xml" + ) if os.path.exists(infile): GenericXML.read(self, infile) diff --git a/CIME/build_scripts/buildlib.pio b/CIME/build_scripts/buildlib.pio index b04367b7b19..90a1b202900 100755 --- a/CIME/build_scripts/buildlib.pio +++ b/CIME/build_scripts/buildlib.pio @@ -105,7 +105,11 @@ def buildlib(bldroot, installpath, case): elif pio_version == 1: cmake_opts = '"-D GENF90_PATH=$CIMEROOT/CIME/non_py/externals/genf90 "' else: - cmake_opts = '"-D GENF90_PATH=' + srcroot + '/libraries/parallelio/scripts/ "' + cmake_opts = ( + '"-DCMAKE_POLICY_VERSION_MINIMUM=3.5 -D GENF90_PATH=' + + srcroot + + '/libraries/parallelio/scripts/ "' + ) stdargs = get_standard_makefile_args(case, shared_lib=True) diff --git a/CIME/tests/test_sys_bless_tests_results.py b/CIME/tests/test_sys_bless_tests_results.py index 2f2beeb461d..fd96754304d 100644 --- a/CIME/tests/test_sys_bless_tests_results.py +++ b/CIME/tests/test_sys_bless_tests_results.py @@ -214,5 +214,5 @@ def test_rebless_namelist(self): # Basic namelist compare should now pass again self._create_test(compargs) - - self.verify_perms(self._baseline_area) + if self._config.test_mode == "e3sm": + self.verify_perms(self._baseline_area) diff --git a/CIME/utils.py b/CIME/utils.py index 61808eb8779..a7cdcf91ec9 100644 --- a/CIME/utils.py +++ b/CIME/utils.py @@ -221,9 +221,9 @@ def check_name(fullname, additional_chars=None, fullpath=False): # Should only be called from get_cime_config() -def _read_cime_config_file(): +def _read_cime_config_file(configdir=".cime"): """ - READ the config file in ~/.cime, this file may contain + READ the config file in configdir, this file may contain [main] CIME_MODEL=e3sm,cesm,ufs PROJECT=someprojectnumber @@ -271,7 +271,7 @@ def _read_cime_config_file(): ) cime_config_file = os.path.abspath( - os.path.join(os.path.expanduser("~"), ".cime", "config") + os.path.join(os.path.expanduser("~"), configdir, "config") ) cime_config = configparser.ConfigParser() if os.path.isfile(cime_config_file): @@ -279,8 +279,8 @@ def _read_cime_config_file(): for section in cime_config.sections(): expect( section in allowed_sections, - "Unknown section {} in .cime/config\nallowed sections are {}".format( - section, allowed_sections + "Unknown section {} in {}/config\nallowed sections are {}".format( + section, configdir, allowed_sections ), ) if cime_config.has_section("main"): @@ -309,10 +309,21 @@ def _read_cime_config_file(): _CIMECONFIG = None +def get_config_dir(): + commit = get_current_commit( + repo=os.path.abspath(os.path.join(get_cime_root(), "..")), tag=True + ) + if commit.startswith("cesm") or commit.startswith("e3sm"): + configdir = "." + commit[0:5] + if not os.path.isdir(os.path.join(os.path.expanduser("~"), configdir)): + configdir = ".cime" + return configdir + + def get_cime_config(): global _CIMECONFIG if not _CIMECONFIG: - _CIMECONFIG = _read_cime_config_file() + _CIMECONFIG = _read_cime_config_file(configdir=get_config_dir()) return _CIMECONFIG @@ -343,7 +354,7 @@ def copy_local_macros_to_dir(destination, extra_machdir=None): dotcime = None home = os.environ.get("HOME") if home: - dotcime = os.path.join(home, ".cime") + dotcime = os.path.join(home, get_config_dir()) if dotcime and os.path.isdir(dotcime): local_macros.extend(glob.glob(dotcime + "/*.cmake")) @@ -447,7 +458,9 @@ def get_cime_default_driver(): driver = cime_config.get("main", "CIME_DRIVER") if driver: logger.debug( - "Setting CIME_driver={} from ~/.cime/config".format(driver) + "Setting CIME_driver={} from ~/{}/config".format( + driver, get_config_dir() + ) ) from CIME.config import Config @@ -529,7 +542,11 @@ def get_model(): if cime_config.has_option("main", "CIME_MODEL"): model = cime_config.get("main", "CIME_MODEL") if model is not None: - logger.debug("Setting CIME_MODEL={} from ~/.cime/config".format(model)) + logger.debug( + "Setting CIME_MODEL={} from ~/{}/config".format( + model, get_config_dir() + ) + ) # One last try if model is None: @@ -554,7 +571,9 @@ def get_model(): modelroot = os.path.join(get_cime_root(), "CIME", "config") models = os.listdir(modelroot) - msg = ".cime/config or environment variable CIME_MODEL must be set to one of: " + msg = "{}/config or environment variable CIME_MODEL must be set to one of: ".format( + get_config_dir() + ) msg += ", ".join( [ model @@ -1559,7 +1578,9 @@ def get_project(machobj=None): if cime_config.has_option("main", "PROJECT"): project = cime_config.get("main", "PROJECT") if project is not None: - logger.info("Using project from .cime/config: " + project) + logger.info( + "Using project from {}/config: {}".format(get_config_dir(), project) + ) return project projectfile = os.path.abspath(os.path.join(os.path.expanduser("~"), ".cesm_proj")) @@ -1613,7 +1634,11 @@ def get_charge_account(machobj=None, project=None): if cime_config.has_option("main", "CHARGE_ACCOUNT"): charge_account = cime_config.get("main", "CHARGE_ACCOUNT") if charge_account is not None: - logger.info("Using charge_account from .cime/config: " + charge_account) + logger.info( + "Using charge_account from {}/config: {}".format( + get_config_dir(), charge_account + ) + ) return charge_account if machobj is not None: @@ -2585,7 +2610,9 @@ def get_htmlroot(machobj=None): if cime_config.has_option("main", "CIME_HTML_ROOT"): htmlroot = cime_config.get("main", "CIME_HTML_ROOT") if htmlroot is not None: - logger.info("Using htmlroot from .cime/config: {}".format(htmlroot)) + logger.info( + "Using htmlroot from {}/config: {}".format(get_config_dir(), htmlroot) + ) return htmlroot if machobj is not None: @@ -2615,7 +2642,9 @@ def get_urlroot(machobj=None): if cime_config.has_option("main", "CIME_URL_ROOT"): urlroot = cime_config.get("main", "CIME_URL_ROOT") if urlroot is not None: - logger.info("Using urlroot from .cime/config: {}".format(urlroot)) + logger.info( + "Using urlroot from {}/config: {}".format(get_config_dir(), urlroot) + ) return urlroot if machobj is not None: