aboutsummaryrefslogtreecommitdiff
path: root/doc-tool
diff options
context:
space:
mode:
authorFelix Mulder <felix.mulder@gmail.com>2017-01-09 15:27:08 +0100
committerFelix Mulder <felix.mulder@gmail.com>2017-01-31 14:31:05 +0100
commit51a22ba302184937f4b7930cc7db60b2ab353e71 (patch)
tree340af479d8998eed925689d569d61c24f9ff54d9 /doc-tool
parentce4ba7f7718fb1b5f698e784fa7f89902f5bf098 (diff)
downloaddotty-51a22ba302184937f4b7930cc7db60b2ab353e71.tar.gz
dotty-51a22ba302184937f4b7930cc7db60b2ab353e71.tar.bz2
dotty-51a22ba302184937f4b7930cc7db60b2ab353e71.zip
Implement `{% include 'template' %}` feature
Diffstat (limited to 'doc-tool')
-rw-r--r--doc-tool/resources/_includes/header.html1
-rw-r--r--doc-tool/src/dotty/tools/dottydoc/staticsite/LiquidTemplate.scala46
-rw-r--r--doc-tool/src/dotty/tools/dottydoc/staticsite/Page.scala11
-rw-r--r--doc-tool/src/dotty/tools/dottydoc/staticsite/ResourceFinder.scala16
-rw-r--r--doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala46
-rw-r--r--doc-tool/test/dotty/tools/dottydoc/staticsite/PageTests.scala14
-rw-r--r--doc-tool/test/dotty/tools/dottydoc/staticsite/SiteTests.scala32
7 files changed, 125 insertions, 41 deletions
diff --git a/doc-tool/resources/_includes/header.html b/doc-tool/resources/_includes/header.html
new file mode 100644
index 000000000..219cdf7f9
--- /dev/null
+++ b/doc-tool/resources/_includes/header.html
@@ -0,0 +1 @@
+<h1>Some header</h1>
diff --git a/doc-tool/src/dotty/tools/dottydoc/staticsite/LiquidTemplate.scala b/doc-tool/src/dotty/tools/dottydoc/staticsite/LiquidTemplate.scala
new file mode 100644
index 000000000..18ef9ef2a
--- /dev/null
+++ b/doc-tool/src/dotty/tools/dottydoc/staticsite/LiquidTemplate.scala
@@ -0,0 +1,46 @@
+package dotty.tools
+package dottydoc
+package staticsite
+
+import dotc.config.Printers.dottydoc
+
+case class LiquidTemplate(contents: String) extends ResourceFinder {
+ import scala.collection.JavaConverters._
+ import liqp.{ Template, TemplateContext }
+ import liqp.nodes.LNode
+ import liqp.tags.Tag
+
+ def render(params: Map[String, AnyRef], includes: Map[String, String]): String = {
+ Template.parse(contents).`with`(ResourceInclude(params, includes)).render(params.asJava)
+ }
+
+ private case class ResourceInclude(params: Map[String, AnyRef], includes: Map[String, String])
+ extends Tag("include") {
+ val DefaultExtension = ".html"
+
+ private def renderTemplate(template: String) = "dude"
+
+ override def render(ctx: TemplateContext, nodes: LNode*): AnyRef = {
+ val origInclude = asString(nodes(0).render(ctx))
+ val incResource = origInclude match {
+ case fileWithExt if fileWithExt.indexOf('.') > 0 => fileWithExt
+ case file => file + DefaultExtension
+ }
+
+ includes
+ .get(incResource)
+ .map { template =>
+ val additionalParams =
+ // include has `with` clause:
+ if (nodes.length > 1) params + (origInclude -> nodes(1).render(ctx))
+ else params
+
+ Template.parse(template, ctx.flavor).render(additionalParams.asJava)
+ }
+ .getOrElse {
+ /*dottydoc.*/println(s"couldn't find include file '$origInclude'")
+ ""
+ }
+ }
+ }
+}
diff --git a/doc-tool/src/dotty/tools/dottydoc/staticsite/Page.scala b/doc-tool/src/dotty/tools/dottydoc/staticsite/Page.scala
index 0293c3367..c8148c627 100644
--- a/doc-tool/src/dotty/tools/dottydoc/staticsite/Page.scala
+++ b/doc-tool/src/dotty/tools/dottydoc/staticsite/Page.scala
@@ -9,7 +9,6 @@ import dotc.config.Printers.dottydoc
import com.vladsch.flexmark.html.HtmlRenderer
import com.vladsch.flexmark.parser.Parser
import com.vladsch.flexmark.ext.front.matter.AbstractYamlFrontMatterVisitor
-import liqp.{ Template => LiquidTemplate }
import _root_.java.util.{ Map => JMap }
case class IllegalFrontMatter(message: String) extends Exception(message)
@@ -17,7 +16,7 @@ case class IllegalFrontMatter(message: String) extends Exception(message)
trait Page {
import scala.collection.JavaConverters._
-
+ def includes: Map[String, String]
def pageContent: String
def params: Map[String, AnyRef]
@@ -61,9 +60,7 @@ trait Page {
// make accessible via "{{ page.title }}" in templates
val page = Map("page" -> _yaml.asJava)
- _html = LiquidTemplate
- .parse(withoutYaml)
- .render((params ++ page).asJava)
+ _html = LiquidTemplate(withoutYaml).render(params ++ page, includes)
}
/** Takes "page" from `params` map in case this is a second expansion, and
@@ -81,11 +78,11 @@ trait Page {
.getOrElse(newYaml)
}
-class HtmlPage(fileContents: => String, val params: Map[String, AnyRef]) extends Page {
+class HtmlPage(fileContents: => String, val params: Map[String, AnyRef], val includes: Map[String, String]) extends Page {
lazy val pageContent = fileContents
}
-class MarkdownPage(fileContents: => String, val params: Map[String, AnyRef]) extends Page {
+class MarkdownPage(fileContents: => String, val params: Map[String, AnyRef], val includes: Map[String, String]) extends Page {
lazy val pageContent = fileContents
override protected[this] def initFields()(implicit ctx: Context) = {
diff --git a/doc-tool/src/dotty/tools/dottydoc/staticsite/ResourceFinder.scala b/doc-tool/src/dotty/tools/dottydoc/staticsite/ResourceFinder.scala
new file mode 100644
index 000000000..66d31fa18
--- /dev/null
+++ b/doc-tool/src/dotty/tools/dottydoc/staticsite/ResourceFinder.scala
@@ -0,0 +1,16 @@
+package dotty.tools
+package dottydoc
+package staticsite
+
+trait ResourceFinder {
+ /** If, for some reason, the supplied default files cannot be found - this
+ * exception will be thrown in `layouts`.
+ */
+ final case class ResourceNotFoundException(message: String) extends Exception(message)
+
+ protected def getResource(r: String): String =
+ Option(getClass.getResourceAsStream(r)).map(scala.io.Source.fromInputStream)
+ .map(_.mkString)
+ .getOrElse(throw ResourceNotFoundException(r))
+
+}
diff --git a/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala b/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala
index ac609e6b6..b1962735f 100644
--- a/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala
+++ b/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala
@@ -7,12 +7,7 @@ import dotc.config.Printers.dottydoc
import dotc.core.Contexts.Context
import scala.io.Source
-class Site(val root: JFile) {
-
- /** If, for some reason, the supplied default files cannot be found - this
- * exception will be thrown in `layouts`.
- */
- final case class ResourceNotFoundException(message: String) extends Exception(message)
+class Site(val root: JFile) extends ResourceFinder {
/** Files that define a layout then referred to by `layout: filename-no-ext`
* in yaml front-matter.
@@ -24,19 +19,10 @@ class Site(val root: JFile) {
* defaults, the user-defined one will take precedence.
*/
val layouts: Map[String, String] = {
- def collectLayouts(dir: JFile): Map[String, String] =
- dir
- .listFiles
- .filter(f => f.getName.endsWith(".md") || f.getName.endsWith(".html"))
- .map { f =>
- (f.getName.substring(0, f.getName.lastIndexOf('.')), Source.fromFile(f).mkString)
- }
- .toMap
-
val userDefinedLayouts =
root
.listFiles.find(d => d.getName == "_layouts" && d.isDirectory)
- .map(collectLayouts)
+ .map(collectFiles(_, f => f.endsWith(".md") || f.endsWith(".html")))
.getOrElse(Map.empty)
val defaultLayouts: Map[String, String] = Map(
@@ -47,10 +33,28 @@ class Site(val root: JFile) {
defaultLayouts ++ userDefinedLayouts
}
- private def getResource(r: String): String =
- Option(getClass.getResourceAsStream(r)).map(scala.io.Source.fromInputStream)
- .map(_.mkString)
- .getOrElse(throw ResourceNotFoundException(r))
+ val includes: Map[String, String] = {
+ val userDefinedIncludes =
+ root
+ .listFiles.find(d => d.getName == "_includes" && d.isDirectory)
+ .map(collectFiles(_, f => f.endsWith(".md") || f.endsWith(".html")))
+ .getOrElse(Map.empty)
+
+ val defaultIncludes: Map[String, String] = Map(
+ "header.html" -> "/_includes/header.html"
+ ).mapValues(getResource)
+
+ defaultIncludes ++ userDefinedIncludes
+ }
+
+ private def collectFiles(dir: JFile, includes: String => Boolean): Map[String, String] =
+ dir
+ .listFiles
+ .filter(f => includes(f.getName))
+ .map { f =>
+ (f.getName.substring(0, f.getName.lastIndexOf('.')), Source.fromFile(f).mkString)
+ }
+ .toMap
def render(page: Page, params: Map[String, AnyRef])(implicit ctx: Context): String = {
page.yaml.get("layout").flatMap(layouts.get(_)) match {
@@ -58,7 +62,7 @@ class Site(val root: JFile) {
page.html
case Some(layout) =>
val newParams = Map("content" -> page.html) ++ params ++ Map("page" -> page.yaml)
- val expandedTemplate = new HtmlPage(layout, newParams)
+ val expandedTemplate = new HtmlPage(layout, newParams, includes)
render(expandedTemplate, params)
}
}
diff --git a/doc-tool/test/dotty/tools/dottydoc/staticsite/PageTests.scala b/doc-tool/test/dotty/tools/dottydoc/staticsite/PageTests.scala
index 87358d738..6f20e28c2 100644
--- a/doc-tool/test/dotty/tools/dottydoc/staticsite/PageTests.scala
+++ b/doc-tool/test/dotty/tools/dottydoc/staticsite/PageTests.scala
@@ -15,6 +15,7 @@ class PageTests extends DottyDocTest {
|---
|
|great""".stripMargin,
+ Map.empty,
Map.empty
)
@@ -33,7 +34,8 @@ class PageTests extends DottyDocTest {
|---
|
|{{ content }}""".stripMargin,
- Map("content" -> "Hello, world!")
+ Map("content" -> "Hello, world!"),
+ Map.empty
)
assert(
@@ -45,7 +47,8 @@ class PageTests extends DottyDocTest {
val page2 = new MarkdownPage(
"""|{{ content }}""".stripMargin,
- Map("content" -> "hello")
+ Map("content" -> "hello"),
+ Map.empty
)
assert(
page2.yaml == Map(),
@@ -57,7 +60,8 @@ class PageTests extends DottyDocTest {
"""|{% if product.title == "Awesome Shoes" %}
|These shoes are awesome!
|{% endif %}""".stripMargin,
- Map("product" -> Map("title" -> "Awesome Shoes").asJava)
+ Map("product" -> Map("title" -> "Awesome Shoes").asJava),
+ Map.empty
)
assertEquals(
@@ -67,7 +71,7 @@ class PageTests extends DottyDocTest {
}
@Test def simpleHtmlPage = {
- val p1 = new HtmlPage("""<h1>{{ "hello, world!" }}</h1>""", Map.empty)
+ val p1 = new HtmlPage("""<h1>{{ "hello, world!" }}</h1>""", Map.empty, Map.empty)
assert(p1.yaml == Map(), "non-empty yaml found")
assertEquals("<h1>hello, world!</h1>", p1.html)
}
@@ -79,6 +83,7 @@ class PageTests extends DottyDocTest {
|---
|
|Hello, world!""".stripMargin,
+ Map.empty,
Map.empty
)
@@ -93,6 +98,7 @@ class PageTests extends DottyDocTest {
|
|
|Hello, world!""".stripMargin,
+ Map.empty,
Map.empty
)
diff --git a/doc-tool/test/dotty/tools/dottydoc/staticsite/SiteTests.scala b/doc-tool/test/dotty/tools/dottydoc/staticsite/SiteTests.scala
index 2a8b6ac9b..0c6d232f5 100644
--- a/doc-tool/test/dotty/tools/dottydoc/staticsite/SiteTests.scala
+++ b/doc-tool/test/dotty/tools/dottydoc/staticsite/SiteTests.scala
@@ -6,6 +6,12 @@ import org.junit.Test
import org.junit.Assert._
class SiteTests extends DottyDocTest {
+ private def html(
+ str: String,
+ params: Map[String, AnyRef] = Map.empty,
+ includes: Map[String, String] = Map.empty
+ ) = new HtmlPage(str, params, includes)
+
@Test def hasCorrectLayoutFiles = {
val site = new Site(new java.io.File("../doc-tool/resources/"))
@@ -20,13 +26,12 @@ class SiteTests extends DottyDocTest {
@Test def renderHelloInMainLayout = {
val site = new Site(new java.io.File("../doc-tool/resources/"))
- val renderedPage = site.render(new HtmlPage(
+ val renderedPage = site.render(html(
"""|---
|layout: main
|---
|
- |Hello, world!""".stripMargin,
- Map.empty
+ |Hello, world!""".stripMargin
), Map.empty)
assert(
@@ -40,12 +45,11 @@ class SiteTests extends DottyDocTest {
@Test def renderMultipleTemplates = {
val site = new Site(new java.io.File("../doc-tool/resources/"))
- val renderedPage = site.render(new HtmlPage(
+ val renderedPage = site.render(html(
"""|---
|layout: index
|---
- |Hello, world!""".stripMargin,
- Map.empty
+ |Hello, world!""".stripMargin
), Map.empty)
assert(
@@ -60,13 +64,12 @@ class SiteTests extends DottyDocTest {
@Test def preservesPageYaml = {
val site = new Site(new java.io.File("../doc-tool/resources/"))
- val renderedPage = site.render(new HtmlPage(
+ val renderedPage = site.render(html(
"""|---
|title: Hello, world
|layout: index
|---
- |Hello, world!""".stripMargin,
- Map.empty
+ |Hello, world!""".stripMargin
), Map.empty)
assert(
@@ -78,4 +81,15 @@ class SiteTests extends DottyDocTest {
"html page did not render properly"
)
}
+
+ @Test def include = {
+ val site = new Site(new java.io.File("../doc-tool/resources/"))
+
+ val renderedInclude = site.render(
+ html("""{% include "header.html" %}""", includes = site.includes),
+ Map.empty
+ )
+
+ assertEquals("<h1>Some header</h1>\n", renderedInclude)
+ }
}