Repository: ESMCI/cime

Issue:
Do not allow + in casename
I thought that this was already in a list of characters not allowed in casename but apparently it isn't


Discussion:
It is called out as a verboten character in the CESM casename conventions:

http://www.cesm.ucar.edu/models/cesm2.0/cesm/casename_conventions_cesm.html

`*** IMPORTANT NOTE: none of strings delimited by a "." in the casename should contain any of these special wildcard characters +,*,?,{,} that are used by the CESM scripts in pattern matching. *** `

but I don't see it mentioned anywhere in the CIME documentation anywhere.  

I'll add it to the doc but do we also need a check in create_newcase, create_test, and create_clone?
The casename check is here https://github.com/ESMCI/cime/blob/356cec0eb9605496b08271a66e39b074373d972e/scripts/lib/CIME/utils.py#L117   I think we just need to add a + sign...
CIME should document forbidden case name characters.  Any additional conventions would be in model-specific documentation.
So @rljacob would you agree to this list of forbidden chars for cime casenames?
  
+*?<>/{}[\]~`@:
Yes.
This should go into the user's guide as an important note. @rljacob - can
you add this when you add your documentation for hybrid/branch?

On Thu, Apr 12, 2018 at 6:33 AM, jedwards4b <notifications@github.com>
wrote:

> So @rljacob <https://github.com/rljacob> would you agree to this list of
> forbidden chars for cime casenames?
>
> +*?<>/{}[]~`@:
>
> —
> You are receiving this because you are subscribed to this thread.
> Reply to this email directly, view it on GitHub
> <https://github.com/ESMCI/cime/issues/2452#issuecomment-380788822>, or mute
> the thread
> <https://github.com/notifications/unsubscribe-auth/AHlxEwumzTnWCFdQ50R0cce5DG_JqXGkks5tn0mBgaJpZM4TQ0EA>
> .
>


Resolving patch:
diff --git a/scripts/lib/CIME/case/case_clone.py b/scripts/lib/CIME/case/case_clone.py
--- a/scripts/lib/CIME/case/case_clone.py
+++ b/scripts/lib/CIME/case/case_clone.py
@@ -3,7 +3,7 @@
 """
 import os, glob, shutil
 from CIME.XML.standard_module_setup import *
-from CIME.utils import expect
+from CIME.utils import expect, check_name
 from CIME.user_mod_support import apply_user_mods
 from CIME.locked_files         import lock_file
 from CIME.simple_compare            import compare_files
@@ -28,6 +28,8 @@ def create_clone(self, newcase, keepexe=False, mach_dir=None, project=None,
     expect(not os.path.isdir(newcaseroot),
            "New caseroot directory {} already exists".format(newcaseroot))
     newcasename = os.path.basename(newcaseroot)
+    expect(check_name(newcasename),
+           "New case name invalid {} ".format(newcasename))
     newcase_cimeroot = os.path.abspath(get_cime_root())
 
     # create clone from case to case
diff --git a/scripts/lib/CIME/utils.py b/scripts/lib/CIME/utils.py
--- a/scripts/lib/CIME/utils.py
+++ b/scripts/lib/CIME/utils.py
@@ -126,9 +126,15 @@ def check_name(fullname, additional_chars=None, fullpath=False):
     True
     >>> check_name("/some/file/path/case.name", fullpath=True)
     True
+    >>> check_name("mycase+mods")
+    False
+    >>> check_name("mycase?mods")
+    False
+    >>> check_name("mycase*mods")
+    False
     """
 
-    chars = '<>/{}[\]~`@:' # pylint: disable=anomalous-backslash-in-string
+    chars = '+*?<>/{}[\]~`@:' # pylint: disable=anomalous-backslash-in-string
     if additional_chars is not None:
         chars += additional_chars
     if fullpath:


Test patch: