Q: WordBoundary issue in StringReplace Why does the following StringReplace pattern match: 
StringReplace["blah *hello* blah", ("*" ~~ ShortestMatch[str__] ~~ "*") :> 
    ("<u>" <> str <> "</u>")]
(* blah <u>hello</u> blah *)

but not when bracketing the pattern with WordBoundary:
StringReplace["blah *hello* blah", (WordBoundary ~~ "*" ~~ 
    ShortestMatch[str__] ~~ "*" ~~ WordBoundary) :> ("<u>" <> str <> "</u>")]
(* "blah *hello* blah" *)


A: It doesn't work because what you want to match is the Whitespace not the Wordboundary. In fact, you really don't need WordBoundary because your "*hello*" is surrounded by Whitespace. This means, if the word you want to match, happens to be at the end of a line, WordBoundary would prevent the match. Therefore, the only thing you need is WhiteSpace
StringReplace["blah *hello* blah", 
 (Whitespace ~~ "*" ~~ Shortest[str__] ~~ "*" ~~ Whitespace) :> 
  (" <u>" <> str <> "</u> ")]

If you realy are keen to use it, you have to take care of the Whitespace too
StringReplace["blah *hello* blah", 
 (WordBoundary ~~ Whitespace ~~ 
    "*" ~~ Shortest[str__] ~~ "*" ~~ 
  Whitespace ~~ WordBoundary) 
 :> (" <u>" <> str <> "</u> ")]

