aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohannes Rudolph <johannes.rudolph@gmail.com>2014-07-08 15:19:20 +0200
committerJohannes Rudolph <johannes.rudolph@gmail.com>2014-07-08 15:19:20 +0200
commitdf2ad7c83b8cc1ef00e1e0fc446121879057d77d (patch)
tree80d021b86b02f58a4294af5a1c92d3f24ccc27db
parent79587ca29b48b9c62dfbcaa6ad3318f623e156a6 (diff)
downloadsbt-boilerplate-df2ad7c83b8cc1ef00e1e0fc446121879057d77d.tar.gz
sbt-boilerplate-df2ad7c83b8cc1ef00e1e0fc446121879057d77d.tar.bz2
sbt-boilerplate-df2ad7c83b8cc1ef00e1e0fc446121879057d77d.zip
add support for custom ranges
-rw-r--r--src/main/scala/spray/boilerplate/Generator.scala8
-rw-r--r--src/main/scala/spray/boilerplate/TemplateParser.scala21
-rw-r--r--src/test/scala/spray/boilerplate/GeneratorSpecs.scala12
-rw-r--r--src/test/scala/spray/boilerplate/TemplateParserSpecs.scala3
4 files changed, 36 insertions, 8 deletions
diff --git a/src/main/scala/spray/boilerplate/Generator.scala b/src/main/scala/spray/boilerplate/Generator.scala
index b115002..5576f56 100644
--- a/src/main/scala/spray/boilerplate/Generator.scala
+++ b/src/main/scala/spray/boilerplate/Generator.scala
@@ -13,9 +13,9 @@ object Generator {
generate(TemplateParser.parse(template))(expandTo)
def generate(format: TemplateElement)(idx: Int): String = format match {
- case Sequence(els @ _*) ⇒ els.map(e ⇒ generate(e)(idx)).mkString
- case Expand(inner, sep) ⇒ (1 to idx).map(generate(inner)).mkString(sep)
- case Offset(i) ⇒ (idx + i - 1).toString
- case LiteralString(lit) ⇒ lit
+ case Sequence(els @ _*) ⇒ els.map(e ⇒ generate(e)(idx)).mkString
+ case Expand(inner, sep, range) ⇒ (range.start.getOrElse(1) to range.end.getOrElse(idx)).map(generate(inner)).mkString(sep)
+ case Offset(i) ⇒ (idx + i - 1).toString
+ case LiteralString(lit) ⇒ lit
}
}
diff --git a/src/main/scala/spray/boilerplate/TemplateParser.scala b/src/main/scala/spray/boilerplate/TemplateParser.scala
index 6d8e22d..8808bc8 100644
--- a/src/main/scala/spray/boilerplate/TemplateParser.scala
+++ b/src/main/scala/spray/boilerplate/TemplateParser.scala
@@ -19,8 +19,14 @@ case class Sequence(elements: TemplateElement*) extends TemplateElement {
case class LiteralString(literal: String) extends TemplateElement
/* An offset to be replaced by the current index */
case class Offset(i: Int) extends TemplateElement
+
+case class Range(start: Option[Int] = None, end: Option[Int] = None)
+
/** A region in which to apply expansions */
-case class Expand(inner: TemplateElement, separator: String = Expand.defaultSeparator) extends TemplateElement
+case class Expand(
+ inner: TemplateElement,
+ separator: String = Expand.defaultSeparator,
+ range: Range = Range(None, None)) extends TemplateElement
object Expand {
val defaultSeparator = ", "
}
@@ -36,7 +42,7 @@ object TemplateParser extends RegexParsers {
def offset: Parser[Offset] = offsetChars ^^ (s ⇒ Offset(s.toInt))
def literalString: Parser[LiteralString] = rep1(escapedLiteralNumber | literalChar) ^^ (chs ⇒ LiteralString(chs.mkString))
def literalChar: Parser[Char] =
- not("[#" | """#[^\]]*\]""".r | offsetChars) ~> elem("Any character", _ ⇒ true)
+ not(expandStart | """#[^\]]*\]""".r | offsetChars) ~> elem("Any character", _ ⇒ true)
def offsetChars = "[012]".r
@@ -44,9 +50,16 @@ object TemplateParser extends RegexParsers {
def outsideTemplate: Parser[LiteralString] = """(?s).+?(?=(\[#)|(\z))""".r ^^ (LiteralString(_))
- def expand: Parser[Expand] = "[#" ~> elements ~ "#" ~ separatorChars <~ "]" ^^ {
- case els ~ x ~ sep ⇒ Expand(els, sep.getOrElse(Expand.defaultSeparator))
+ def expand: Parser[Expand] = expandStart ~ elements ~ "#" ~ separatorChars <~ "]" ^^ {
+ case range ~ els ~ x ~ sep ⇒ Expand(els, sep.getOrElse(Expand.defaultSeparator), range)
}
+ def expandStart: Parser[Range] = "[" ~> range <~ "#"
+
+ def range: Parser[Range] =
+ (opt("""\d{1,2}""".r) ~ """\s*\.\.\s*""".r ~ opt("""\d{1,2}""".r) ^^ {
+ case start ~ sep ~ end ⇒ Range(start.map(_.toInt), end.map(_.toInt))
+ }) | success(Range())
+
def outsideElements: Parser[TemplateElement] =
rep1(expand | outsideTemplate) ^^ maybeSequence
diff --git a/src/test/scala/spray/boilerplate/GeneratorSpecs.scala b/src/test/scala/spray/boilerplate/GeneratorSpecs.scala
index d88010b..d1f6af8 100644
--- a/src/test/scala/spray/boilerplate/GeneratorSpecs.scala
+++ b/src/test/scala/spray/boilerplate/GeneratorSpecs.scala
@@ -28,6 +28,18 @@ class GeneratorSpecs extends Specification {
"support custom separator" in {
gen4("[#a1#.]") === "a1.a2.a3.a4"
}
+ "support custom range start" in {
+ gen4("[2..#a1#.]") === "a2.a3.a4"
+ }
+ "support custom range end" in {
+ gen4("[..6#a1#.]") === "a1.a2.a3.a4.a5.a6"
+ }
+ "support custom range" in {
+ gen4("[5..10#a1#.]") === "a5.a6.a7.a8.a9.a10"
+ }
+ "support inner custom range" in {
+ gen4("[#a1([2..#T1#])#]") === "a1(), a2(T2), a3(T2, T3), a4(T2, T3, T4)"
+ }
}
def gen4(template: String): String = Generator.generateFromTemplate(template, 4)
diff --git a/src/test/scala/spray/boilerplate/TemplateParserSpecs.scala b/src/test/scala/spray/boilerplate/TemplateParserSpecs.scala
index 85b99af..fbf6ee2 100644
--- a/src/test/scala/spray/boilerplate/TemplateParserSpecs.scala
+++ b/src/test/scala/spray/boilerplate/TemplateParserSpecs.scala
@@ -25,5 +25,8 @@ class TemplateParserSpecs extends Specification {
"a quoted number" in {
parse("[#T##1#]") === Expand(LiteralString("T1"))
}
+ "custom range" in {
+ parse("[0..11#T1#]") === Expand(LiteralString("T") ~ Offset(1), range = Range(start = Some(0), end = Some(11)))
+ }
}
}