New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Using cats-parse with Scala string interpolation #179
Comments
If I were parsing this, I would do something like: // parse expressions like names, `{1 + 1}` etc...
val pexpr: Parser[Expr] = ...
sealed trait Element
case class ExprEl(toExpr: Expr) extends Element
case class StringEl(toStr: String) extends Element
val pstr: Parser[List[Element]] = {
import cats.parse.{Parser => P}
val notDollar = P.not(P.charIn('\\' :: '"' :: Nil)).with1 *> ((P.char('\\') *> P.anyChar) | P.anyChar)
val strEl: P[StringEl] = notDollar.repAs[String].map(StringEl(_))
val expr: P[ExprEl] = P.char('$') *> pexpr.map(ExprEl(_))
P.string("json") *> (strEl | expr).rep <* P.char('"')
} Something like that... Does that make sense (warning, I didn't compile this, I just wrote it in the comment). |
Sorry, I think I didn't make my question clear enough. At https://docs.scala-lang.org/overviews/core/string-interpolation.html#advanced-usage implicit class JsonHelper(val sc: StringContext) extends AnyVal {
def json(args: Any*): JSONObject = {
val strings = sc.parts.iterator
val expressions = args.iterator
var buf = new StringBuilder(strings.next())
while(strings.hasNext) {
buf.append(expressions.next())
buf.append(strings.next())
}
parseJson(buf)
}
} The challenge here is that we don't have a single input string to parse, but two iterators: one for the string snippets, and one for the elements that separate these snippets.
The How do I use |
I really don't know how this library might relate to what you are proposing. I mean, you might want to parse the result of that string? so, are you talking about how to implement parseJson? I'd probably say it is better to use a library like circe or jawn for that. |
@johnynek well, all this is about parsing a (slightly fancy) json string into a data structure, isn't it? @michel-steuwer i think the "slightly fancy" will be a problem here: what you get from StringContext is more structured than a plain string, and you'd want to make use of this additional structure. one way to attack that problem is concatenating the template literal strings, interspersed with some private unicode markers. |
Yeah. We only support String as an input (since it is by far the most common case and it we can optimize it considerably). If you want to see an example parser for a structured type, see the JSON parser here: https://github.com/typelevel/cats-parse/blob/main/bench/src/main/scala/cats/parse/bench/self.scala Lastly, what I would do here is to just convert the whole interpolated argument to a string and then run the parser on that string. |
How would I best use
cats-parse
with Scalas string interpolation feature, where the input I am parsing is not just a plain string but also arbitrary values that are interpolated in it?So how would I best write a parser for something like:
from https://docs.scala-lang.org/overviews/core/string-interpolation.html#advanced-usage
The text was updated successfully, but these errors were encountered: