How to insert double quotes into String with interpolation in scala
This is a bug in Scala:
escape does not work with string interpolation
but maybe you can use:
scala> import org.apache.commons.lang.StringEscapeUtils.escapeJava
import org.apache.commons.lang.StringEscapeUtils.escapeJava
scala> escapeJava("this is a string\nover two lines")
res1: java.lang.String = this is a string\nover two lines
You don't need to escape quotes in triple-quoted string, so s""""$value"""""
will work. Admittedly, it doesn't look good either.
Another solution (also mentioned in the Scala tracker) is to use
case _ => s"${'"'}$value${'"'}"
Still ugly, but sometimes perhaps may be preferred over triple quotes.
It seems an escape sequence $"
was suggested as a part of SIP-24 for 2.12:
case _ => s"$"$value$""
This SIP was never accepted, as it contained other more controversial suggestions. Currently there is an effort to get escape sequence $"
implemented in 2.13 as Pre SIP/mini SIP $” escapes in interpolations.
For your use case, they make it easy to achieve nice syntax.
scala> implicit class `string quoter`(val sc: StringContext) {
| def q(args: Any*): String = "\"" + sc.s(args: _*) + "\""
| }
defined class string$u0020quoter
scala> q"hello,${" "*8}world"
res0: String = "hello, world"
scala> "hello, world"
res1: String = hello, world // REPL doesn't add the quotes, sanity check
scala> " hello, world "
res2: String = " hello, world " // unless the string is untrimmed
Squirrel the implicit away in a package object somewhere.
You can name the interpolator something besides q
, of course.
Last week, someone asked on the ML for the ability to use backquoted identifiers. Right now you can do res3 but not res4:
scala> val `"` = "\""
": String = "
scala> s"${`"`}"
res3: String = "
scala> s"hello, so-called $`"`world$`"`"
res4: String = hello, so-called "world"
Another idea that just occurred to me was that the f-interpolator already does some work to massage your string. For instance, it has to handle "%n" intelligently. It could, at the same time, handle an additional escape "%q" which it would not pass through to the underlying formatter.
That would look like:
scala> f"%qhello, world%q"
<console>:9: error: conversions must follow a splice; use %% for literal %, %n for newline
That's worth an enhancement request.
Update: just noticed that octals aren't deprecated in interpolations yet:
scala> s"\42hello, world\42"
res12: String = "hello, world"