-
Notifications
You must be signed in to change notification settings - Fork 90
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
add option to use other renderer easily
- Loading branch information
Showing
8 changed files
with
212 additions
and
125 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
package sbtbuildinfo | ||
|
||
case class ScalaCaseClassRenderer(options: Seq[BuildInfoOption], pkg: String, obj: String) extends ScalaRenderer { | ||
override def fileType = BuildInfoType.Source | ||
override def extension = "scala" | ||
|
||
val traitNames = options.collect{case BuildInfoOption.Traits(ts @ _*) => ts}.flatten | ||
val objTraits = if (traitNames.isEmpty) "" else " extends " ++ traitNames.mkString(" with ") | ||
|
||
// It is safe to add `import scala.Predef` even though we need to keep `-Ywarn-unused-import` in mind | ||
// because we always generate code that has a reference to `String`. If the "base" generated code were to be | ||
// changed and no longer contain a reference to `String`, we would need to remove `import scala.Predef` and | ||
// fully qualify every reference. Note it is NOT safe to use `import scala._` because of the possibility of | ||
// the project using `-Ywarn-unused-import` because we do not always generated references that are part of | ||
// `scala` such as `scala.Option`. | ||
def header = List( | ||
s"package $pkg", | ||
"", | ||
"import scala.Predef._", | ||
"", | ||
s"/** This file was generated by sbt-buildinfo. */" | ||
) | ||
|
||
override def renderKeys(buildInfoResults: Seq[BuildInfoResult]) = | ||
header ++ | ||
caseClassDefinitionBegin ++ | ||
buildInfoResults.flatMap(caseClassParameter).mkString(",\n").split("\n") ++ | ||
caseClassDefinitionEnd ++ | ||
toMapMethod(buildInfoResults) ++ | ||
caseClassEnd ++ | ||
List("") ++ | ||
caseObjectLine(buildInfoResults) | ||
|
||
private def caseClassDefinitionBegin = List( | ||
s"case class $obj$objTraits(" | ||
) | ||
|
||
private def caseClassParameter(r: BuildInfoResult): Seq[String] = { | ||
val typeDecl = getType(r.typeExpr) getOrElse "Any" | ||
|
||
List( | ||
s" ${r.identifier}: $typeDecl" | ||
) | ||
} | ||
|
||
private def toMapMethod(results: Seq[BuildInfoResult]) = | ||
if (options.contains(BuildInfoOption.ToMap)) | ||
results | ||
.map(result => " \"%s\" -> %s".format(result.identifier, result.identifier)) | ||
.mkString(" def toMap: Map[String, Any] = Map[String, Any](\n", ",\n", ")") | ||
.split("\n") | ||
.toList ::: List("") | ||
else Nil | ||
|
||
private def caseClassDefinitionEnd = List(") {", "") | ||
private def caseClassEnd = List("}") | ||
|
||
private def caseObjectLine(buildInfoResults: Seq[BuildInfoResult]) = List( | ||
s"case object $obj {", | ||
s" val data: $obj = new $obj(${buildInfoResults.map(_.value).map(quote).mkString(",")})", | ||
s"}" | ||
) | ||
|
||
def toMapLine(results: Seq[BuildInfoResult]): Seq[String] = | ||
if (options.contains(BuildInfoOption.ToMap) || options.contains(BuildInfoOption.ToJson)) | ||
results | ||
.map(result => " \"%s\" -> %s".format(result.identifier, result.identifier)) | ||
.mkString(" val toMap: Map[String, Any] = Map[String, Any](\n", ",\n", ")") | ||
.split("\n") | ||
.toList ::: List("") | ||
else Nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,68 @@ | ||
package sbtbuildinfo | ||
|
||
private[sbtbuildinfo] case class ScalaCaseObjectRenderer(options: Seq[BuildInfoOption], pkg: String, obj: String) extends ScalaRenderer { | ||
|
||
override def fileType = BuildInfoType.Source | ||
override def extension = "scala" | ||
val traitNames = options.collect{case BuildInfoOption.Traits(ts @ _*) => ts}.flatten | ||
val objTraits = if (traitNames.isEmpty) "" else " extends " ++ traitNames.mkString(" with ") | ||
|
||
// It is safe to add `import scala.Predef` even though we need to keep `-Ywarn-unused-import` in mind | ||
// because we always generate code that has a reference to `String`. If the "base" generated code were to be | ||
// changed and no longer contain a reference to `String`, we would need to remove `import scala.Predef` and | ||
// fully qualify every reference. Note it is NOT safe to use `import scala._` because of the possibility of | ||
// the project using `-Ywarn-unused-import` because we do not always generated references that are part of | ||
// `scala` such as `scala.Option`. | ||
def header = List( | ||
s"package $pkg", | ||
"", | ||
"import scala.Predef._", | ||
"", | ||
s"/** This object was generated by sbt-buildinfo. */", | ||
s"case object $obj$objTraits {" | ||
) | ||
|
||
def footer = List("}") | ||
|
||
override def renderKeys(buildInfoResults: Seq[BuildInfoResult]) = | ||
header ++ | ||
buildInfoResults.flatMap(line) ++ Seq(toStringLines(buildInfoResults)) ++ | ||
toMapLine(buildInfoResults) ++ toJsonLine ++ | ||
footer | ||
|
||
private def line(result: BuildInfoResult): Seq[String] = { | ||
import result._ | ||
val typeDecl = getType(result.typeExpr) map { ": " + _ } getOrElse "" | ||
|
||
List( | ||
s" /** The value is ${quote(value)}. */", | ||
s" val $identifier$typeDecl = ${quote(value)}" | ||
) | ||
} | ||
|
||
def toStringLines(results: Seq[BuildInfoResult]): String = { | ||
val idents = results.map(_.identifier) | ||
val fmt = idents.map("%s: %%s" format _).mkString(", ") | ||
val vars = idents.mkString(", ") | ||
s""" override val toString: String = { | ||
| "$fmt" format ( | ||
| $vars | ||
| ) | ||
| }""".stripMargin | ||
} | ||
|
||
def toMapLine(results: Seq[BuildInfoResult]): Seq[String] = | ||
if (options.contains(BuildInfoOption.ToMap) || options.contains(BuildInfoOption.ToJson)) | ||
results | ||
.map(result => " \"%s\" -> %s".format(result.identifier, result.identifier)) | ||
.mkString(" val toMap: Map[String, Any] = Map[String, Any](\n", ",\n", ")") | ||
.split("\n") | ||
.toList ::: List("") | ||
else Nil | ||
|
||
def toJsonLine: Seq[String] = | ||
if (options contains BuildInfoOption.ToJson) | ||
List(""" val toJson: String = toMap.map(i => "\"" + i._1 + "\":\"" + i._2 + "\"").mkString("{", ", ", "}")""") | ||
else Nil | ||
|
||
} |
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
package sbtbuildinfo | ||
|
||
/** | ||
* Created by akos on 1/6/17. | ||
*/ | ||
abstract class ScalaRenderer extends BuildInfoRenderer { | ||
protected def getType(typeExpr: TypeExpression): Option[String] = { | ||
def tpeToReturnType(tpe: TypeExpression): Option[String] = | ||
tpe match { | ||
case TypeExpression("Any", Nil) => None | ||
case TypeExpression("Int", Nil) => Some("scala.Int") | ||
case TypeExpression("Long", Nil) => Some("scala.Long") | ||
case TypeExpression("Double", Nil) => Some("scala.Double") | ||
case TypeExpression("Boolean", Nil) => Some("scala.Boolean") | ||
case TypeExpression("scala.Symbol", Nil) => Some("scala.Symbol") | ||
case TypeExpression("java.lang.String", Nil) => Some("String") | ||
case TypeExpression("java.net.URL", Nil) => Some("java.net.URL") | ||
case TypeExpression("sbt.URL", Nil) => Some("java.net.URL") | ||
case TypeExpression("java.io.File", Nil) => Some("java.io.File") | ||
case TypeExpression("sbt.File", Nil) => Some("java.io.File") | ||
case TypeExpression("scala.xml.NodeSeq", Nil) => Some("scala.xml.NodeSeq") | ||
|
||
case TypeExpression("sbt.ModuleID", Nil) => Some("String") | ||
case TypeExpression("sbt.Resolver", Nil) => Some("String") | ||
|
||
case TypeExpression("scala.Option", Seq(arg)) => | ||
tpeToReturnType(arg) map { x => s"scala.Option[$x]" } | ||
case TypeExpression("scala.collection.Seq", Seq(arg)) => | ||
tpeToReturnType(arg) map { x => s"scala.collection.Seq[$x]" } | ||
case TypeExpression("scala.collection.immutable.Map", Seq(arg0, arg1)) => | ||
for { | ||
x0 <- tpeToReturnType(arg0) | ||
x1 <- tpeToReturnType(arg1) | ||
} yield s"Map[$x0, $x1]" | ||
case TypeExpression("scala.Tuple2", Seq(arg0, arg1)) => | ||
for { | ||
x0 <- tpeToReturnType(arg0) | ||
x1 <- tpeToReturnType(arg1) | ||
} yield s"($x0, $x1)" | ||
case _ => None | ||
} | ||
tpeToReturnType(typeExpr) | ||
} | ||
|
||
protected def quote(v: Any): String = v match { | ||
case x @ ( _: Int | _: Double | _: Boolean | _: Symbol) => x.toString | ||
case x: Long => x.toString + "L" | ||
case node: scala.xml.NodeSeq if node.toString().trim.nonEmpty => node.toString() | ||
case (k, _v) => "(%s -> %s)" format(quote(k), quote(_v)) | ||
case mp: Map[_, _] => mp.toList.map(quote(_)).mkString("Map(", ", ", ")") | ||
case seq: Seq[_] => seq.map(quote).mkString("scala.collection.Seq(", ", ", ")") | ||
case op: Option[_] => op map { x => "scala.Some(" + quote(x) + ")" } getOrElse {"scala.None"} | ||
case url: java.net.URL => "new java.net.URL(%s)" format quote(url.toString) | ||
case file: java.io.File => "new java.io.File(%s)" format quote(file.toString) | ||
case s => "\"%s\"" format encodeStringLiteral(s.toString) | ||
} | ||
|
||
protected def encodeStringLiteral(str: String): String = | ||
str.replace("\\","\\\\").replace("\n","\\n").replace("\b","\\b").replace("\r","\\r"). | ||
replace("\t","\\t").replace("\'","\\'").replace("\f","\\f").replace("\"","\\\"") | ||
|
||
|
||
} |