Microsoft Developer Network > Forums Home > Windows Azure Forums > Windows Azure Storage, CDN and Caching > What regular expression could I use to validate a blob container name?

Answered What regular expression could I use to validate a blob container name?

Answers

  • Thursday, May 05, 2011 1:46 AM
     
     Answered Has Code

    It turns out that neither of the previous two answers are correct.  Regular expressions are really tricky to get "correct". :)  You can test this regular expression carefully using your favorite regular expression tool (RegEx Buddy, RegEx Coach, etc.)


    // Container names must be valid DNS names, and must conform to these rules:
    // * Container names must start with a letter or number, and can contain only letters, numbers, and the dash (-) character.
    // * Every dash (-) character must be immediately preceded and followed by a letter or number; consecutive dashes are not permitted in container names.
    // * All letters in a container name must be lowercase.
    // * Container names must be from 3 through 63 characters long.
    
    // $root is a special container that can exist at the root level and is always valid.
    if (containerName.Equals("$root"))
     return; 
    
    if (!Regex.IsMatch(containerName, @"^[a-z0-9](([a-z0-9\-[^\-])){1,61}[a-z0-9]$"))
     throw new Exception("Invalid container name);
    
    
    • Proposed As Answer by Lee J Grissom Thursday, May 05, 2011 1:48 AM
    • Marked As Answer by tjrobinson Thursday, May 05, 2011 9:12 AM
    • Edited by Lee J Grissom Thursday, May 05, 2011 9:03 PM Clarified my comment on $root container
    •  
  • Friday, July 29, 2011 11:03 AM
     
     Answered

    I realise that this is a year too late, but I was recently performing the same check and came across this page!

    I think that in order to ensure that you can match the dashes correctly, you need to use a "zero-width positive lookahead" - (?=x) syntax.

    I think this RegEx should work:

    ^(([a-z\d]((-(?=[a-z\d]))|([a-z\d])){2,62})|(\$root))$

     

    I have combined the check for the $root container name.

    The regex uses grouping and the positive look ahead.

    It matches either a [letter or number] as the first match, this must then be followed by (EITHER (a dash followed by a [letter or number]) OR ([a letter or number])) - it MUST have at least two matches of this to a maximum of 62, giving 63 total characters.

    • Proposed As Answer by Jonathan.Blair Thursday, August 11, 2011 1:11 PM
    • Marked As Answer by tjrobinson Thursday, August 11, 2011 2:58 PM
    •  

All Replies

  • Friday, May 28, 2010 5:48 PM
     
      Has Code

    Try this:

    ^([a-z]|\d){1}([a-z]|-|\d){1,61}([a-z]|\d){1}$

    or you can use this function:

    internal static bool IsBlobContainerNameValid(string name)
        {
          if (name.Equals("$root"))
          { 
            return true; 
          }
          string validBlobContainerNameRegex = @"^([a-z]|\d){1}([a-z]|-|\d){1,61}([a-z]|\d){1}$";
          Regex reg = new Regex(validBlobContainerNameRegex);
          if (reg.IsMatch(name))
          {
            return true;
          }
          return false;
        }

    Hope this helps

    Thanks

    Gaurav Mantri

    Cerebrata Software

    http://www.cerebrata.com

    • Marked As Answer by tjrobinson Tuesday, June 01, 2010 8:43 AM
    • Unmarked As Answer by tjrobinson Thursday, May 05, 2011 9:12 AM
    •  
  • Tuesday, September 28, 2010 3:25 PM
     
     Proposed Answer Has Code

    I think this is not enough.

    The code above do not handle the fact a dash character must be immediately preceded and followed by a letter or number.

    For example, the following string will be returned as a correct container name whereas it should not : "a--b"

     

    Therefore, I recommend to use this code:

    /// <summary>Checks that containerName is a valid DNS name, as requested by Azure</summary>
        public static bool IsContainerNameValid(string containerName)
        {
          return (Regex.IsMatch(containerName, @"(^([a-z]|\d))((-([a-z]|\d)|([a-z]|\d))+)$") 
            && (3 <= containerName.Length) && (containerName.Length <= 63));
        }

    Matthieu Durut

    Lokad

    http://www.lokad.com

     

    • Proposed As Answer by Matthieu Durut Tuesday, September 28, 2010 3:28 PM
    •  
  • Thursday, May 05, 2011 1:46 AM
     
     Answered Has Code

    It turns out that neither of the previous two answers are correct.  Regular expressions are really tricky to get "correct". :)  You can test this regular expression carefully using your favorite regular expression tool (RegEx Buddy, RegEx Coach, etc.)


    // Container names must be valid DNS names, and must conform to these rules:
    // * Container names must start with a letter or number, and can contain only letters, numbers, and the dash (-) character.
    // * Every dash (-) character must be immediately preceded and followed by a letter or number; consecutive dashes are not permitted in container names.
    // * All letters in a container name must be lowercase.
    // * Container names must be from 3 through 63 characters long.
    
    // $root is a special container that can exist at the root level and is always valid.
    if (containerName.Equals("$root"))
     return; 
    
    if (!Regex.IsMatch(containerName, @"^[a-z0-9](([a-z0-9\-[^\-])){1,61}[a-z0-9]$"))
     throw new Exception("Invalid container name);
    
    
    • Proposed As Answer by Lee J Grissom Thursday, May 05, 2011 1:48 AM
    • Marked As Answer by tjrobinson Thursday, May 05, 2011 9:12 AM
    • Edited by Lee J Grissom Thursday, May 05, 2011 9:03 PM Clarified my comment on $root container
    •  
  • Friday, July 29, 2011 11:03 AM
     
     Answered

    I realise that this is a year too late, but I was recently performing the same check and came across this page!

    I think that in order to ensure that you can match the dashes correctly, you need to use a "zero-width positive lookahead" - (?=x) syntax.

    I think this RegEx should work:

    ^(([a-z\d]((-(?=[a-z\d]))|([a-z\d])){2,62})|(\$root))$

     

    I have combined the check for the $root container name.

    The regex uses grouping and the positive look ahead.

    It matches either a [letter or number] as the first match, this must then be followed by (EITHER (a dash followed by a [letter or number]) OR ([a letter or number])) - it MUST have at least two matches of this to a maximum of 62, giving 63 total characters.

    • Proposed As Answer by Jonathan.Blair Thursday, August 11, 2011 1:11 PM
    • Marked As Answer by tjrobinson Thursday, August 11, 2011 2:58 PM
    •