views:

171

answers:

2

Our clients have a string stored in their registry which is an executable command. The string may or may not have quotes around the target path, and may or may not have parameters. For example:

"C:\path\file.exe" param1=value1 param2=value2
C:\path\file.exe param1=value1 param2=value2
"C:\path\file.exe"
C:\path\file.exe
"C:\path\file with spaces.exe" param1=value1 param2=value2
"C:\path\file with spaces.exe"

I need to get the directory of the target path, i.e. C:\path.

  • I tried Path.GetDirectoryName, but that fails with "Illegal characters in path."
  • I also tried creating a ProcessStartInfo object, but that doesn't seem to have the smarts to parse the string.
  • I fiddled with Uri, but didn't have any luck there either.

I have a solution using a regular expression (which I will post below as an answer), but this seems like a "there-must-be-a-built-in-.Net-helper-class-for-this" problem.

Is there a class I'm missing, or just not using the classes above correctly?

+1  A: 

Here's a regular expression that is working. But, like I said in my question, is there a better way? Or are there cases where this will fail?

Regex pattern = new Regex(@"^(?<quot>"")?(?<path>(?(quot)[^""]|\S)*)", RegexOptions.ExplicitCapture);
var match = pattern.Match(value);
return Path.GetDirectoryName(match.Groups["path"].Value);
Dave
Looks quite OK to me for the specific task at hand.
Lucero
A: 

I had posted:

var strings = value.Split(" ", 2);
var firstString = strings.Length == 0 ? string.Empty : strings[0];
return Path.GetDirectoryName(firstString ); 

But then I slapped myself.

Then I saw http://community.bartdesmet.net/blogs/bart/archive/2009/02/21/net-4-0-system-shell-commandline-parsing-part-1.aspx any use? (doesnt look like it handles this aspect of the parsing though, and it doesnt actually exist!)

None of the standard System.IO classes provide any of the type of parsing you're looking for so I say your regex is fine unless someone can locate a common one.

Looking in Reflector, all the System.Environment code that does command line parsing seems to be Native, so I'd be pretty confident you're not missing any standard APIs for this purpose - this type of consideration (how file names are represented) is considered external to .NET (which makes sense as it's platform specific).

Ruben Bartelink