From 87f1f5f44585e855a8c8234955e1e48dcbbc3a21 Mon Sep 17 00:00:00 2001 From: Felix Mulder Date: Fri, 6 Jan 2017 13:57:00 +0100 Subject: Add beginnings of Site class --- doc-tool/resources/_layouts/main.html | 37 +++++++++++++ .../src/dotty/tools/dottydoc/staticsite/Site.scala | 62 ++++++++++++++++++++++ doc-tool/test/StaticSiteTests.scala | 40 ++++++++++++++ 3 files changed, 139 insertions(+) create mode 100644 doc-tool/resources/_layouts/main.html create mode 100644 doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala create mode 100644 doc-tool/test/StaticSiteTests.scala diff --git a/doc-tool/resources/_layouts/main.html b/doc-tool/resources/_layouts/main.html new file mode 100644 index 000000000..1920f9ce7 --- /dev/null +++ b/doc-tool/resources/_layouts/main.html @@ -0,0 +1,37 @@ + + + + + + + + {{ page.title }} + + + + + + {{ content }} + + + + + + diff --git a/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala b/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala new file mode 100644 index 000000000..d51b881e5 --- /dev/null +++ b/doc-tool/src/dotty/tools/dottydoc/staticsite/Site.scala @@ -0,0 +1,62 @@ +package dotty.tools +package dottydoc +package staticsite + +import _root_.java.io.{ File => JFile } +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) + + /** Files that define a layout then referred to by `layout: filename-no-ext` + * in yaml front-matter. + * + * The compiler will look in two locations, `/_layouts/` and + * in the bundled jar file's resources `/_layouts`. + * + * If the user supplies a layout that has the same name as one of the + * 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 + + def getResource(p: String): String = + Option(getClass.getResourceAsStream(p)).map(scala.io.Source.fromInputStream) + .map(_.mkString) + .getOrElse(throw ResourceNotFoundException(p)) + + val userDefinedLayouts = + root + .listFiles.find(d => d.getName == "_layouts" && d.isDirectory) + .map(collectLayouts) + .getOrElse(Map.empty) + + val defaultLayouts: Map[String, String] = Map( + "main" -> "/_layouts/main.html" + ).mapValues(getResource) + + defaultLayouts ++ userDefinedLayouts + } + + def render(page: Page, params: Map[String, AnyRef])(implicit ctx: Context): String = { + page.yaml.get("layout").flatMap(layouts.get(_)) match { + case Some(layout) => + (new HtmlPage(layout, Map("content" -> page.html) ++ params)).html + case None => + page.html + } + } +} diff --git a/doc-tool/test/StaticSiteTests.scala b/doc-tool/test/StaticSiteTests.scala new file mode 100644 index 000000000..a2f174eb3 --- /dev/null +++ b/doc-tool/test/StaticSiteTests.scala @@ -0,0 +1,40 @@ +package dotty.tools +package dottydoc + +import org.junit.Test +import org.junit.Assert._ + +import staticsite.{ Site, HtmlPage } + +class StaticSiteTests extends DottyDocTest { + @Test def hasCorrectLayoutFiles = { + val site = new Site(new java.io.File("../doc-tool/resources/")) + + assert(site.root.exists && site.root.isDirectory, + s"'${site.root.getName}' is not a directory") + + val expectedLayouts = Set("main") + assert(site.layouts.keys == expectedLayouts, + s"Incorrect layouts in: ${site.layouts.keys}, expected: $expectedLayouts") + } + + @Test def renderHelloInMainLayout = { + val site = new Site(new java.io.File("../doc-tool/resources/")) + + val renderedPage = site.render(new HtmlPage( + """|--- + |layout: main + |--- + | + |Hello, world!""".stripMargin, + Map.empty + ), Map.empty) + + assert( + renderedPage.contains("Hello, world!") && + !renderedPage.contains("---\nlayout: main\n---\n") && + renderedPage.contains(""), + "html page did not render properly" + ) + } +} -- cgit v1.2.3