You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@juneau.apache.org by ja...@apache.org on 2018/04/13 14:27:20 UTC

[juneau] branch master updated: JUNEAU-82 Configurable look-and-feel

This is an automated email from the ASF dual-hosted git repository.

jamesbognar pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/juneau.git


The following commit(s) were added to refs/heads/master by this push:
     new b1c429a  JUNEAU-82 Configurable look-and-feel
b1c429a is described below

commit b1c429ae03a5f50e23ecae22fe7e2f6caba4332d
Author: JamesBognar <ja...@apache.org>
AuthorDate: Fri Apr 13 10:27:14 2018 -0400

    JUNEAU-82 Configurable look-and-feel
---
 .../apache/juneau/dto/swagger/ui/SwaggerUI.java    |   8 +-
 .../juneau/utils/ClasspathResourceFinderBasic.java |  13 +-
 .../utils/ClasspathResourceFinderRecursive.java    |   5 +
 .../utils/ClasspathResourceFinderSimple.java       |   5 +
 juneau-doc/src/main/javadoc/overview.html          |   8 +-
 juneau-examples/juneau-examples-rest/examples.cfg  |  20 +-
 .../files/htdocs/images}/asf.png                   | Bin
 .../files/htdocs/images}/juneau.png                | Bin
 .../files/htdocs/styles/SwaggerUI.css              | 341 +++++++++++++++++++++
 .../files/htdocs/themes}/dark.css                  |   0
 .../files/htdocs/themes}/devops.css                |   0
 .../files/htdocs/themes}/light.css                 |   0
 .../files/htdocs/themes}/original.css              |   0
 .../juneau-examples-rest/{ => files}/jetty.xml     |   3 -
 .../juneau/examples/rest/AtomFeedResource.java     |   4 +-
 .../juneau/examples/rest/DirectoryResource.java    |   4 +-
 .../juneau/examples/rest/JsonSchemaResource.java   |   4 +-
 .../juneau/examples/rest/PetStoreResource.java     |   6 +-
 .../examples/rest/PredefinedLabelsResource.java    |   4 +-
 .../juneau/examples/rest/RequestEchoResource.java  |   4 +-
 .../apache/juneau/examples/rest/RootResources.java |   8 +-
 .../juneau/examples/rest/SqlQueryResource.java     |   4 +-
 .../juneau/examples/rest/StaticFilesResource.java  |   4 +-
 .../examples/rest/SystemPropertiesResource.java    |   4 +-
 .../juneau/examples/rest/TempDirResource.java      |   4 +-
 .../examples/rest/UrlEncodedFormResource.java      |   4 +-
 .../rest/addressbook/AddressBookResource.java      |   4 +-
 .../examples/rest/petstore/PetStoreResource.java   |   4 +-
 .../juneau/examples/rest/RootContentTest.java      |  18 +-
 .../files/htdocs/images}/asf.png                   | Bin
 .../files/htdocs/images}/juneau.png                | Bin
 .../files/htdocs/styles/SwaggerUI.css              | 341 +++++++++++++++++++++
 .../files/htdocs/themes}/dark.css                  |   0
 .../files/htdocs/themes}/devops.css                |   0
 .../files/htdocs/themes}/light.css                 |   0
 .../files/htdocs/themes}/original.css              |   0
 .../{ => files}/jetty.xml                          |   0
 .../my-microservice.cfg                            |  19 +-
 .../src/assembly/bin.xml                           |   1 +
 .../juneau/microservice/sample/RootResources.java  |   4 +-
 .../juneau-microservice-test/{ => files}/jetty.xml |   0
 .../juneau-microservice-test.cfg                   |   4 +-
 .../org/apache/juneau/rest/BasicRestConfig.java    |  11 +-
 .../org/apache/juneau/rest/BasicRestServlet.java   |   4 -
 .../juneau/rest/widget/ContentTypeMenuItem.java    |   2 +-
 .../apache/juneau/rest/widget/PoweredByApache.java |  62 ----
 .../apache/juneau/rest/widget/QueryMenuItem.java   |   2 +-
 .../{StyleMenuItem.java => ThemeMenuItem.java}     |  12 +-
 .../rest/{styles => htdocs/themes}/devops.css      |   0
 49 files changed, 799 insertions(+), 146 deletions(-)

diff --git a/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/ui/SwaggerUI.java b/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/ui/SwaggerUI.java
index 3a026e1..945e306 100644
--- a/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/ui/SwaggerUI.java
+++ b/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/ui/SwaggerUI.java
@@ -66,7 +66,7 @@ public class SwaggerUI extends PojoSwap<Swagger,Div> {
 	public static final String SWAGGERUI_resolveRefsMaxDepth = PREFIX + "resolveRefsMaxDepth.i";
 
 	
-	static final ClasspathResourceManager RESOURCES = new ClasspathResourceManager(SwaggerUI.class);
+	static final ClasspathResourceManager RESOURCES = new ClasspathResourceManager(SwaggerUI.class, ClasspathResourceFinderBasic.INSTANCE, Boolean.getBoolean("RestContext.useClasspathResourceCaching.b"));
 	
 	private static final Set<String> STANDARD_METHODS = new ASet<String>().appendAll("get", "put", "post", "delete", "options");
 	
@@ -90,8 +90,12 @@ public class SwaggerUI extends PojoSwap<Swagger,Div> {
 		
 		Session s = new Session(beanSession, swagger);
 		
+		String css = RESOURCES.getString("files/htdocs/styles/SwaggerUI.css");
+		if (css == null)
+			css = RESOURCES.getString("SwaggerUI.css");
+		
 		Div outer = div(
-			style(RESOURCES.getString("SwaggerUI.css")),
+			style(css),
 			script("text/javascript", RESOURCES.getString("SwaggerUI.js")),
 			header(s)
 		)._class("swagger-ui");
diff --git a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderBasic.java b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderBasic.java
index 327540e..50defd6 100644
--- a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderBasic.java
+++ b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderBasic.java
@@ -19,18 +19,23 @@ import java.util.*;
  * Utility class for finding resources for a class.
  * 
  * <p>
- * Same as {@link ClasspathResourceFinderSimple}, but if the resource cannot be found in the classpath, then an attempt 
- * is made to look in the JVM working directory.
+ * Same as {@link ClasspathResourceFinderSimple}, but first searches the working directory for the file before
+ * looking in the classpath.
  * <br>Path traversals outside the working directory are not allowed for security reasons.
  */
 public class ClasspathResourceFinderBasic extends ClasspathResourceFinderSimple {
+	
+	/**
+	 * Reusable instance.
+	 */
+	public static final ClasspathResourceFinderBasic INSTANCE = new ClasspathResourceFinderBasic();
 
 	@Override /* ClasspathResourceFinder */
 	public InputStream findResource(Class<?> baseClass, String name, Locale locale) throws IOException {
-		InputStream is = findClasspathResource(baseClass, name, locale);
+		InputStream is = findFileSystemResource(name, locale);
 		if (is != null)
 			return is;
-		return findFileSystemResource(name, locale);
+		return findClasspathResource(baseClass, name, locale);
 	}
 	
 	/**
diff --git a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderRecursive.java b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderRecursive.java
index b023dcb..79be8e4 100644
--- a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderRecursive.java
+++ b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderRecursive.java
@@ -20,6 +20,11 @@ import java.util.*;
  */
 public class ClasspathResourceFinderRecursive extends ClasspathResourceFinderBasic {
 
+	/**
+	 * Reusable instance.
+	 */
+	public static final ClasspathResourceFinderRecursive INSTANCE = new ClasspathResourceFinderRecursive();
+
 	@Override /* ResourceFinder2 */
 	public InputStream findResource(Class<?> baseClass, String name, Locale locale) throws IOException {
 		while (baseClass != null) {
diff --git a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderSimple.java b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderSimple.java
index fb9f2fc..11e74fb 100644
--- a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderSimple.java
+++ b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/utils/ClasspathResourceFinderSimple.java
@@ -36,6 +36,11 @@ import java.util.ResourceBundle.*;
  */
 public class ClasspathResourceFinderSimple implements ClasspathResourceFinder {
 
+	/**
+	 * Reusable instance.
+	 */
+	public static final ClasspathResourceFinderSimple INSTANCE = new ClasspathResourceFinderSimple();
+
 	private static final ResourceBundle.Control RB_CONTROL = ResourceBundle.Control.getControl(Control.FORMAT_DEFAULT);
 	private static final List<Locale> ROOT_LOCALE = Arrays.asList(Locale.ROOT);
 
diff --git a/juneau-doc/src/main/javadoc/overview.html b/juneau-doc/src/main/javadoc/overview.html
index 7c5878c..e7654fb 100644
--- a/juneau-doc/src/main/javadoc/overview.html
+++ b/juneau-doc/src/main/javadoc/overview.html
@@ -21459,6 +21459,12 @@
 				</ul>
 			</ul>
 		</ul>
+
+		<h5 class='topic w800'>juneau-rest-microservice</h5>
+		<ul class='spaced-list'>
+			<li>
+				The look-and-feel of an application is now controlled 
+		</ul>
 	</div>
 	
 	<!-- =========================================================================================================== -->
@@ -22707,7 +22713,7 @@
 						<br><img src='doc-files/ReleaseNotes.631.QueryMenuItem.png'>
 						<br>Fields are now pre-filled with current query parameters.
 					<li>
-						New {@link org.apache.juneau.rest.widget.StyleMenuItem} widget that provides a pull-down menu 
+						New {@link org.apache.juneau.rest.widget.ThemeMenuItem} widget that provides a pull-down menu 
 						with hyperlinks to show the content in the default stylesheets:
 						<br><img src='doc-files/ReleaseNotes.631.StyleMenuItem.png'>
 				</ul>
diff --git a/juneau-examples/juneau-examples-rest/examples.cfg b/juneau-examples/juneau-examples-rest/examples.cfg
index 9be46ca..5336293 100755
--- a/juneau-examples/juneau-examples-rest/examples.cfg
+++ b/juneau-examples/juneau-examples-rest/examples.cfg
@@ -29,7 +29,7 @@ saveConfigAction = RESTART_SERVER
 [Jetty]
 
 # Path of the jetty.xml file used to configure the Jetty server.
-config = jetty.xml
+config = files/jetty.xml
 
 # Resolve Juneau variables in the jetty.xml file.
 resolveVars = true
@@ -45,13 +45,19 @@ port = 10000,0,0,0
 #=======================================================================================================================
 [REST]
 
+staticFiles = htdocs:files/htdocs
+
 # Stylesheet to use for HTML views.
-# The default options are:
-#  - styles/juneau.css
-#  - styles/devops.css
-# Other stylesheets can be referenced relative to the servlet package or working
-# 	directory.
-stylesheet = styles/devops.css
+theme = servlet:/htdocs/themes/devops.css
+
+headerIcon = servlet:/htdocs/images/juneau.png
+headerLink = http://juneau.apache.org
+footerIcon = servlet:/htdocs/images/asf.png
+footerLink = http://www.apache.org
+
+icon = $C{REST/headerIcon}
+header = <a href='$U{$C{REST/headerLink}}'><img src='$U{$C{REST/headerIcon}}' style='position:absolute;top:5;right:5;background-color:transparent;height:30px'/></a>
+footer = <a href='$U{$C{REST/footerLink}}'><img style='float:right;padding-right:20px;height:32px' src='$U{$C{REST/footerIcon}}'>
 
 #=======================================================================================================================
 # Console settings
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/asf.png b/juneau-examples/juneau-examples-rest/files/htdocs/images/asf.png
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/asf.png
copy to juneau-examples/juneau-examples-rest/files/htdocs/images/asf.png
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/juneau.png b/juneau-examples/juneau-examples-rest/files/htdocs/images/juneau.png
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/juneau.png
copy to juneau-examples/juneau-examples-rest/files/htdocs/images/juneau.png
diff --git a/juneau-examples/juneau-examples-rest/files/htdocs/styles/SwaggerUI.css b/juneau-examples/juneau-examples-rest/files/htdocs/styles/SwaggerUI.css
new file mode 100644
index 0000000..7a80655
--- /dev/null
+++ b/juneau-examples/juneau-examples-rest/files/htdocs/styles/SwaggerUI.css
@@ -0,0 +1,341 @@
+/*
+ ***************************************************************************************************************************
+ * Licensed to the Apache Software Foundation (ASF) under one or more contributor license agreements.  See the NOTICE file *
+ * distributed with this work for additional information regarding copyright ownership.  The ASF licenses this file        *
+ * to you under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance            *
+ * with the License.  You may obtain a copy of the License at                                                              *
+ *                                                                                                                         *
+ *  http://www.apache.org/licenses/LICENSE-2.0                                                                             *
+ *                                                                                                                         *
+ * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an  *
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the License for the        *
+ * specific language governing permissions and limitations under the License.                                              *
+ ***************************************************************************************************************************
+*/
+
+.swagger-ui {	
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Header key-value pairs
+ ----------------------------------------------------------------------------------------------------------*/
+
+.swagger-ui table.header {
+    margin-bottom: 15px;
+	width: 95%;
+	border: none;
+}
+
+.swagger-ui table.header * {
+	vertical-align: middle;
+}
+
+.swagger-ui table.header th {
+    font-weight: bold;
+    padding: 5px 10px;
+    text-align: left;
+    white-space: nowrap;
+	border: none;
+	border-radius: 3px;
+}
+
+.swagger-ui table.header td {
+	padding: 5px 10px;
+    text-align: left;
+    vertical-align: middle;
+	border: none;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Method buttons (e.g GET/PUT/... buttons)                                                                
+ ----------------------------------------------------------------------------------------------------------*/
+.method-button {
+  	display: inline-block;
+    font-weight: bold;
+    min-width: 60px;
+    padding: 6px 15px;
+    text-align: center;
+    border-radius: 3px;
+    text-shadow: 0 1px 0 rgba(0,0,0,.1);
+    color: #fff;
+}
+.get .method-button        { background: rgb(97,175,254); }
+.put .method-button        { background: rgb(252,161,48); }
+.post .method-button       { background: rgb(73,204,144); }
+.delete .method-button     { background: rgb(249,62,62); }
+.options .method-button    { background: rgb(153,102,255); }
+.deprecated .method-button { background: rgb(170,170,170); }
+.model .method-button      { background: rgb(150,150,150); min-width: 120px;}
+.other .method-button      { background: rgb(230,230,0); }
+
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Tag block                                                                                                -
+ - Encapsulates one or more op-blocks.
+ ----------------------------------------------------------------------------------------------------------*/
+
+.tag-block {
+	min-width: 800px;
+}
+
+.tag-block-summary {
+	margin: 10px 0px;
+	padding: 5px 0px;
+    align-items: center;
+    cursor: pointer;
+	border-bottom: 1px solid rgba(59,65,81,.2);
+	user-select: none;
+	transition: all .2s;
+}
+.tag-block-summary:hover {
+	background-color: rgba(59,65,81,.1);
+}
+
+.tag-block-summary .name {
+	font-size: 18px;
+	padding: 0px 20px;
+}
+.tag-block-summary .description {
+	font-size: 14px;
+	padding: 0px 20px;
+}
+.tag-block-summary .extdocs {
+	float: right;
+	font-size: 14px;
+	padding: 0px 20px;
+}
+
+.tag-block-open .tag-block-contents { display: block; }
+.tag-block-closed .tag-block-contents { display: none; }
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Op block                                                                                          
+ - Encapsulates a single http-method + http-path
+ ----------------------------------------------------------------------------------------------------------*/
+
+.op-block {
+	margin-bottom: 10px;
+    align-items: center;
+    border-radius: 4px;
+}
+
+.op-block.get        { background: rgba(97,175,254,.1); border: 1px solid rgb(97,175,254); }
+.op-block.put        { background: rgba(252,161,48,.1); border: 1px solid rgb(252,161,48); }
+.op-block.post       { background: rgba(73,204,144,.1); border: 1px solid rgb(73,204,144); }
+.op-block.options    { background: rgba(153,102,255,.1); border: 1px solid rgb(153,102,255); }
+.op-block.delete     { background: rgba(249,62,62,.1); border: 1px solid rgb(249,62,62); }
+.op-block.deprecated { background: rgba(170,170,170,.1); border: 1px solid rgb(170,170,170); }
+.op-block.model      { background: rgba(0,0,0,.05); border: 1px solid rgb(170,170,170); }
+.op-block.other      { background: rgba(230,230,0,0.1); border: 1px solid rgb(230,230,0); }
+
+.op-block-summary {	
+	padding: 5px;
+    cursor: pointer;
+	user-select: none;
+}
+
+.op-block-summary .path {
+	font-size: 14px;
+	word-break: break-all;
+    font-family: monospace;
+    font-weight: bold;
+    padding:10px;
+}
+
+.op-block.deprecated .op-block-summary .path { color: #8f9199; text-decoration: line-through;}
+.op-block.deprecated .op-block-summary .description { color: #8f9199 }
+
+.op-block-summary .summary {
+    font-size: 14px;
+    padding: 10px;
+}
+
+.op-block-description {
+    font-size: 14px;
+    padding: 10px;
+}
+
+
+.op-block-open .op-block-contents { display: block; }
+.op-block-closed .op-block-contents { display: none; }
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Op block section header                                                                                               -
+ - 'Parameters' and 'Responses' subsections in an op-block
+ ----------------------------------------------------------------------------------------------------------*/
+
+.op-block-section-header {
+    padding: 8px 15px;
+    background: hsla(0,0%,100%,.3);
+    box-shadow: 1px 2px 3px rgba(0,0,0,.3);
+    margin: 10px;
+    border-radius: 4px;
+}
+
+.op-block-section-header .title {
+    font-size: 14px;
+    margin: 0px;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Parameters and Responses sections
+ ----------------------------------------------------------------------------------------------------------*/
+
+table.parameters, table.responses {
+    border-collapse: collapse;
+    margin: 20px;
+	width: 95%;
+	border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+th.parameter-key, th.response-key {
+	font-size: 12px;
+    font-weight: bold;
+    text-align: left;
+	border: none;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+	background-color: inherit;
+}
+
+td.parameter-key, td.response-key {
+	font-size: 12px;
+    padding: 10px;
+    text-align: left;
+	border: none;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+	background-color: inherit;
+}
+
+td.parameter-value, td.response-value {
+    padding: 10px;
+    text-align: left;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Parameter name
+ ----------------------------------------------------------------------------------------------------------*/
+
+.parameter-key .in {
+	font-size: 12px;
+    font-family: monospace;
+    font-weight: bold;
+    font-style: italic;
+    color: gray;
+}
+
+.parameter-key .name {
+	font-size: 14px;
+}
+
+.parameter-key .name.required {
+    font-weight: bold;
+}
+
+.parameter-key .requiredlabel {
+	font-size: 10px;
+    color: rgba(255,0,0,.6);    
+    font-weight: bold;
+}
+
+.parameter-key .type {
+    font-size: 12px;
+    padding: 5px 0;
+    font-family: monospace;
+    font-weight: bold;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Examples
+ ----------------------------------------------------------------------------------------------------------*/
+ 
+.op-block-contents .example-select {
+    margin: 10px 0 5px 0;
+	border-width: 1px;
+	font-weight:bold;
+    padding: 5px 40px 5px 10px;
+    border: 1px solid #41444e;
+    border-radius: 4px;
+    box-shadow: 0 1px 2px 0 rgba(0,0,0,.25);
+    background: hsla(0,0%,100%,.3);
+}
+
+.op-block-contents .example-select:disabled {
+    color: rgba(0,0,0,.50);
+    border: 1px solid rgba(0,0,0,.50);
+}
+
+.op-block-contents .example {
+    margin: 0;
+    padding: 5px 20px;
+    white-space: pre-wrap;
+    word-wrap: break-word;
+    hyphens: auto;
+    border-radius: 4px;
+    background: #41444e;
+    overflow-wrap: break-word;
+    font-family: monospace;
+    font-weight: 400;
+    color: #fff;
+	display: none;
+	max-width: 800px;
+	max-height: 800px;
+	text-overflow: auto;
+}
+
+.op-block-contents .example.active {
+	display:block;
+}
+
+.op-block-contents .model {
+	display: none;
+}
+
+.op-block-contents .model.active {
+	display:block;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Headers
+ ----------------------------------------------------------------------------------------------------------*/
+
+.section {
+    font-weight: bold;
+    padding: 5px 0;
+    text-align: left;
+}
+
+.headers .name {
+    padding: 5px 0;
+    font-family: monospace;
+    font-weight: bold;
+}
+
+div.headers {
+	margin: 20px 0px;
+}
+
+.headers .type {
+    padding: 5px 0;
+    font-family: monospace;
+    font-weight: bold;
+}
+
+.section-name {
+	display: inline-block;
+	vertical-align: top;
+	margin-right: 20px;
+    font-weight: bold;
+    padding: 5px 0;
+    text-align: left;
+}
+
+.section-table {
+	display: inline-block;
+}
+
+.responses .section-table td {
+	padding: 5px 20px 5px 0px;
+	text-align: left;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+}
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/dark.css b/juneau-examples/juneau-examples-rest/files/htdocs/themes/dark.css
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/dark.css
copy to juneau-examples/juneau-examples-rest/files/htdocs/themes/dark.css
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/devops.css b/juneau-examples/juneau-examples-rest/files/htdocs/themes/devops.css
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/devops.css
copy to juneau-examples/juneau-examples-rest/files/htdocs/themes/devops.css
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/light.css b/juneau-examples/juneau-examples-rest/files/htdocs/themes/light.css
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/light.css
copy to juneau-examples/juneau-examples-rest/files/htdocs/themes/light.css
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/original.css b/juneau-examples/juneau-examples-rest/files/htdocs/themes/original.css
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/original.css
copy to juneau-examples/juneau-examples-rest/files/htdocs/themes/original.css
diff --git a/juneau-examples/juneau-examples-rest/jetty.xml b/juneau-examples/juneau-examples-rest/files/jetty.xml
similarity index 97%
rename from juneau-examples/juneau-examples-rest/jetty.xml
rename to juneau-examples/juneau-examples-rest/files/jetty.xml
index d3ff1aa..acace45 100644
--- a/juneau-examples/juneau-examples-rest/jetty.xml
+++ b/juneau-examples/juneau-examples-rest/files/jetty.xml
@@ -51,9 +51,6 @@
 					<Item>
 						<New class="org.eclipse.jetty.server.handler.DefaultHandler" />
 					</Item>
-					<Item>
-						<New class="org.eclipse.jetty.server.session.SessionHandler" />
-					</Item>
 				</Array>
 			</Set>
 		</New>
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/AtomFeedResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/AtomFeedResource.java
index cd9b509..08395fa 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/AtomFeedResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/AtomFeedResource.java
@@ -35,13 +35,13 @@ import org.apache.juneau.rest.widget.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		}
 	),
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/DirectoryResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/DirectoryResource.java
index 4db5a15..069da14 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/DirectoryResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/DirectoryResource.java
@@ -38,13 +38,13 @@ import org.apache.juneau.utils.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		}
 	),
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/JsonSchemaResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/JsonSchemaResource.java
index 1a385a4..50b20d9 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/JsonSchemaResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/JsonSchemaResource.java
@@ -30,13 +30,13 @@ import org.apache.juneau.rest.widget.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 		aside={
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PetStoreResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PetStoreResource.java
index 5a1f779..ec57bd1 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PetStoreResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PetStoreResource.java
@@ -44,14 +44,14 @@ import org.apache.juneau.transforms.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class,
+			ThemeMenuItem.class,
 			PetStoreResource.AddPet.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java",
 			"$W{AddPet}"
 		},
@@ -103,7 +103,7 @@ public class PetStoreResource extends BasicRestServletJena {
 			widgets={
 				QueryMenuItem.class,
 				ContentTypeMenuItem.class,
-				StyleMenuItem.class
+				ThemeMenuItem.class
 			},
 
 			navlinks={
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PredefinedLabelsResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PredefinedLabelsResource.java
index 14d3559..af80312 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PredefinedLabelsResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/PredefinedLabelsResource.java
@@ -31,13 +31,13 @@ import org.apache.juneau.rest.widget.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		}
 	),
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RequestEchoResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RequestEchoResource.java
index f12cf49..d325cbf 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RequestEchoResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RequestEchoResource.java
@@ -33,13 +33,13 @@ import org.apache.juneau.transforms.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 		aside={
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RootResources.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RootResources.java
index 0c2612c..e5697a3 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RootResources.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RootResources.java
@@ -29,14 +29,13 @@ import org.apache.juneau.rest.widget.*;
 	description="Example of a router resource page.",
 	htmldoc=@HtmlDoc(
 		widgets={
-			PoweredByApache.class,
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"options: ?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 		aside={
@@ -48,8 +47,7 @@ import org.apache.juneau.rest.widget.*;
 			"	<p>All content on pages in the UI are serialized POJOs.  In this case, it's a serialized array of beans with 2 properties, 'name' and 'description'.</p>",
 			"	<p>Other features (such as this aside) are added through annotations.</p>",
 			"</div>"
-		},
-		footer="$W{PoweredByApache}"
+		}
 	),
 	properties={
 		// For testing purposes, we want to use single quotes in all the serializers so it's easier to do simple
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SqlQueryResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SqlQueryResource.java
index ad05a25..f34839a 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SqlQueryResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SqlQueryResource.java
@@ -39,12 +39,12 @@ import org.apache.juneau.rest.widget.*;
 	description="Executes queries against the local derby '$C{SqlQueryResource/connectionUrl}' database",
 	htmldoc=@HtmlDoc(
 		widgets={ 
-			StyleMenuItem.class 
+			ThemeMenuItem.class 
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/..",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 		aside={
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
index 15c2f08..a501b45 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
@@ -32,13 +32,13 @@ import org.apache.juneau.rest.widget.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{staticFilesResource}.java"
 		}
 	),
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SystemPropertiesResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SystemPropertiesResource.java
index b61d9b1..f381e63 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SystemPropertiesResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/SystemPropertiesResource.java
@@ -40,7 +40,7 @@ import org.apache.juneau.rest.widget.*;
 		// Widget used for content-type and styles pull-down menus.		
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 
 		// Links on the HTML rendition page.
@@ -52,7 +52,7 @@ import org.apache.juneau.rest.widget.*;
 			"options: servlet:/?method=OPTIONS",
 			"form: servlet:/formPage",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/TempDirResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/TempDirResource.java
index 1bf8a5e..a3a3bf7 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/TempDirResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/TempDirResource.java
@@ -38,14 +38,14 @@ import org.apache.juneau.utils.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"upload: servlet:/upload",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 		aside={
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/UrlEncodedFormResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/UrlEncodedFormResource.java
index c08f764..8013dd0 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/UrlEncodedFormResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/UrlEncodedFormResource.java
@@ -34,11 +34,11 @@ import org.apache.juneau.transforms.*;
 	title="URL-Encoded form example",
 	htmldoc=@HtmlDoc(
 		widgets={ 
-			StyleMenuItem.class 
+			ThemeMenuItem.class 
 		},
 		navlinks={
 			"up: request:/..",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/$R{servletClassSimple}.java"
 		},
 		aside={
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/addressbook/AddressBookResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/addressbook/AddressBookResource.java
index 2f272a7..3370f5c 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/addressbook/AddressBookResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/addressbook/AddressBookResource.java
@@ -51,7 +51,7 @@ import org.apache.juneau.utils.*;
 			PoweredByJuneau.class,
 			ContentTypeMenuItem.class,
 			QueryMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 
 		// Links on the HTML rendition page.
@@ -62,7 +62,7 @@ import org.apache.juneau.utils.*;
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/addressbook/$R{servletClassSimple}.java"
 		},
 		
diff --git a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/petstore/PetStoreResource.java b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/petstore/PetStoreResource.java
index 358538c..2e7b5da 100644
--- a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/petstore/PetStoreResource.java
+++ b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/petstore/PetStoreResource.java
@@ -38,13 +38,13 @@ import org.apache.juneau.rest.converters.*;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"up: request:/..",
 			"options: servlet:/?method=OPTIONS",
 			"$W{ContentTypeMenuItem}",
-			"$W{StyleMenuItem}",
+			"$W{ThemeMenuItem}",
 			"source: $C{Source/gitHub}/org/apache/juneau/examples/rest/petstore/$R{servletClassSimple}.java"
 		}
 	),
diff --git a/juneau-examples/juneau-examples-rest/src/test/java/org/apache/juneau/examples/rest/RootContentTest.java b/juneau-examples/juneau-examples-rest/src/test/java/org/apache/juneau/examples/rest/RootContentTest.java
index bfc173c..85097bf 100644
--- a/juneau-examples/juneau-examples-rest/src/test/java/org/apache/juneau/examples/rest/RootContentTest.java
+++ b/juneau-examples/juneau-examples-rest/src/test/java/org/apache/juneau/examples/rest/RootContentTest.java
@@ -26,12 +26,12 @@ public class RootContentTest extends ContentComboTestBase {
 		return Arrays.asList(new Object[][] {
 			{ 	/* 0 */
 				new ComboInput("HTML-stylesheet", "/", MediaType.HTML,
-					"@import '/styles/devops.css';",
+					"@import '/htdocs/themes/devops.css';",
 					".menu-item {"
 				)
 			},
 			{ 	/* 1 */
-				new ComboInput("HTML-stylesheet-contnt", "/styles/devops.css", MediaType.PLAIN,
+				new ComboInput("HTML-stylesheet-contnt", "/htdocs/themes/devops.css", MediaType.PLAIN,
 					"/** DevOps look-and-feel */"
 				)
 			},
@@ -40,7 +40,7 @@ public class RootContentTest extends ContentComboTestBase {
 					"<head>",
 					"<h1>Root resources</h1>",
 					"<h2>Example of a router resource page.</h2>",
-					"<img src='/htdocs/juneau.png' style='position:absolute;top:5;right:5;background-color:transparent;height:30px'/>"
+					"<img src='/htdocs/images/juneau.png' style='position:absolute;top:5;right:5;background-color:transparent;height:30px'/>"
 				)
 			},
 			{ 	/* 3 */
@@ -48,7 +48,7 @@ public class RootContentTest extends ContentComboTestBase {
 					"<nav>",
 					"<a href='/?method=OPTIONS'>options</a>",
 					"<a onclick='menuClick(this)'>content-type</a>",
-					"<a onclick='menuClick(this)'>styles</a>",
+					"<a onclick='menuClick(this)'>themes</a>",
 					"<a href='https://github.com/apache/juneau/blob/master/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/RootResources.java'>source</a>"
 				)
 			},
@@ -60,10 +60,10 @@ public class RootContentTest extends ContentComboTestBase {
 			},
 			{ 	/* 5 */
 				new ComboInput("HTML-nav-popup-styles", "/", MediaType.HTML,
-					"<a href='/?stylesheet=styles%2Fdevops.css'>devops</a>",
-					"<a href='/?stylesheet=styles%2Flight.css'>light</a>",
-					"<a href='/?stylesheet=styles%2Foriginal.css'>original</a>",
-					"<a href='/?stylesheet=styles%2Fdark.css'>dark</a>"
+					"<a href='/?stylesheet=htdocs%2Fthemes%2Fdevops.css'>devops</a>",
+					"<a href='/?stylesheet=htdocs%2Fthemes%2Flight.css'>light</a>",
+					"<a href='/?stylesheet=htdocs%2Fthemes%2Foriginal.css'>original</a>",
+					"<a href='/?stylesheet=htdocs%2Fthemes%2Fdark.css'>dark</a>"
 				)
 			},
 			{ 	/* 6 */
@@ -76,7 +76,7 @@ public class RootContentTest extends ContentComboTestBase {
 			{ 	/* 7 */
 				new ComboInput("HTML-footer", "/", MediaType.HTML,
 					"<footer>",
-					"<img style='float:right;padding-right:20px;height:32px' src='/htdocs/asf.png'>"
+					"<img style='float:right;padding-right:20px;height:32px' src='/htdocs/images/asf.png'>"
 				)
 			},
 			{ 	/* 8 */
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/asf.png b/juneau-microservice/juneau-microservice-template/files/htdocs/images/asf.png
similarity index 100%
rename from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/asf.png
rename to juneau-microservice/juneau-microservice-template/files/htdocs/images/asf.png
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/juneau.png b/juneau-microservice/juneau-microservice-template/files/htdocs/images/juneau.png
similarity index 100%
rename from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/juneau.png
rename to juneau-microservice/juneau-microservice-template/files/htdocs/images/juneau.png
diff --git a/juneau-microservice/juneau-microservice-template/files/htdocs/styles/SwaggerUI.css b/juneau-microservice/juneau-microservice-template/files/htdocs/styles/SwaggerUI.css
new file mode 100644
index 0000000..7a80655
--- /dev/null
+++ b/juneau-microservice/juneau-microservice-template/files/htdocs/styles/SwaggerUI.css
@@ -0,0 +1,341 @@
+/*
+ ***************************************************************************************************************************
+ * Licensed to the Apache Software Foundation (ASF) under one or more contributor license agreements.  See the NOTICE file *
+ * distributed with this work for additional information regarding copyright ownership.  The ASF licenses this file        *
+ * to you under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance            *
+ * with the License.  You may obtain a copy of the License at                                                              *
+ *                                                                                                                         *
+ *  http://www.apache.org/licenses/LICENSE-2.0                                                                             *
+ *                                                                                                                         *
+ * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an  *
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the License for the        *
+ * specific language governing permissions and limitations under the License.                                              *
+ ***************************************************************************************************************************
+*/
+
+.swagger-ui {	
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Header key-value pairs
+ ----------------------------------------------------------------------------------------------------------*/
+
+.swagger-ui table.header {
+    margin-bottom: 15px;
+	width: 95%;
+	border: none;
+}
+
+.swagger-ui table.header * {
+	vertical-align: middle;
+}
+
+.swagger-ui table.header th {
+    font-weight: bold;
+    padding: 5px 10px;
+    text-align: left;
+    white-space: nowrap;
+	border: none;
+	border-radius: 3px;
+}
+
+.swagger-ui table.header td {
+	padding: 5px 10px;
+    text-align: left;
+    vertical-align: middle;
+	border: none;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Method buttons (e.g GET/PUT/... buttons)                                                                
+ ----------------------------------------------------------------------------------------------------------*/
+.method-button {
+  	display: inline-block;
+    font-weight: bold;
+    min-width: 60px;
+    padding: 6px 15px;
+    text-align: center;
+    border-radius: 3px;
+    text-shadow: 0 1px 0 rgba(0,0,0,.1);
+    color: #fff;
+}
+.get .method-button        { background: rgb(97,175,254); }
+.put .method-button        { background: rgb(252,161,48); }
+.post .method-button       { background: rgb(73,204,144); }
+.delete .method-button     { background: rgb(249,62,62); }
+.options .method-button    { background: rgb(153,102,255); }
+.deprecated .method-button { background: rgb(170,170,170); }
+.model .method-button      { background: rgb(150,150,150); min-width: 120px;}
+.other .method-button      { background: rgb(230,230,0); }
+
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Tag block                                                                                                -
+ - Encapsulates one or more op-blocks.
+ ----------------------------------------------------------------------------------------------------------*/
+
+.tag-block {
+	min-width: 800px;
+}
+
+.tag-block-summary {
+	margin: 10px 0px;
+	padding: 5px 0px;
+    align-items: center;
+    cursor: pointer;
+	border-bottom: 1px solid rgba(59,65,81,.2);
+	user-select: none;
+	transition: all .2s;
+}
+.tag-block-summary:hover {
+	background-color: rgba(59,65,81,.1);
+}
+
+.tag-block-summary .name {
+	font-size: 18px;
+	padding: 0px 20px;
+}
+.tag-block-summary .description {
+	font-size: 14px;
+	padding: 0px 20px;
+}
+.tag-block-summary .extdocs {
+	float: right;
+	font-size: 14px;
+	padding: 0px 20px;
+}
+
+.tag-block-open .tag-block-contents { display: block; }
+.tag-block-closed .tag-block-contents { display: none; }
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Op block                                                                                          
+ - Encapsulates a single http-method + http-path
+ ----------------------------------------------------------------------------------------------------------*/
+
+.op-block {
+	margin-bottom: 10px;
+    align-items: center;
+    border-radius: 4px;
+}
+
+.op-block.get        { background: rgba(97,175,254,.1); border: 1px solid rgb(97,175,254); }
+.op-block.put        { background: rgba(252,161,48,.1); border: 1px solid rgb(252,161,48); }
+.op-block.post       { background: rgba(73,204,144,.1); border: 1px solid rgb(73,204,144); }
+.op-block.options    { background: rgba(153,102,255,.1); border: 1px solid rgb(153,102,255); }
+.op-block.delete     { background: rgba(249,62,62,.1); border: 1px solid rgb(249,62,62); }
+.op-block.deprecated { background: rgba(170,170,170,.1); border: 1px solid rgb(170,170,170); }
+.op-block.model      { background: rgba(0,0,0,.05); border: 1px solid rgb(170,170,170); }
+.op-block.other      { background: rgba(230,230,0,0.1); border: 1px solid rgb(230,230,0); }
+
+.op-block-summary {	
+	padding: 5px;
+    cursor: pointer;
+	user-select: none;
+}
+
+.op-block-summary .path {
+	font-size: 14px;
+	word-break: break-all;
+    font-family: monospace;
+    font-weight: bold;
+    padding:10px;
+}
+
+.op-block.deprecated .op-block-summary .path { color: #8f9199; text-decoration: line-through;}
+.op-block.deprecated .op-block-summary .description { color: #8f9199 }
+
+.op-block-summary .summary {
+    font-size: 14px;
+    padding: 10px;
+}
+
+.op-block-description {
+    font-size: 14px;
+    padding: 10px;
+}
+
+
+.op-block-open .op-block-contents { display: block; }
+.op-block-closed .op-block-contents { display: none; }
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Op block section header                                                                                               -
+ - 'Parameters' and 'Responses' subsections in an op-block
+ ----------------------------------------------------------------------------------------------------------*/
+
+.op-block-section-header {
+    padding: 8px 15px;
+    background: hsla(0,0%,100%,.3);
+    box-shadow: 1px 2px 3px rgba(0,0,0,.3);
+    margin: 10px;
+    border-radius: 4px;
+}
+
+.op-block-section-header .title {
+    font-size: 14px;
+    margin: 0px;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Parameters and Responses sections
+ ----------------------------------------------------------------------------------------------------------*/
+
+table.parameters, table.responses {
+    border-collapse: collapse;
+    margin: 20px;
+	width: 95%;
+	border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+th.parameter-key, th.response-key {
+	font-size: 12px;
+    font-weight: bold;
+    text-align: left;
+	border: none;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+	background-color: inherit;
+}
+
+td.parameter-key, td.response-key {
+	font-size: 12px;
+    padding: 10px;
+    text-align: left;
+	border: none;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+	background-color: inherit;
+}
+
+td.parameter-value, td.response-value {
+    padding: 10px;
+    text-align: left;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Parameter name
+ ----------------------------------------------------------------------------------------------------------*/
+
+.parameter-key .in {
+	font-size: 12px;
+    font-family: monospace;
+    font-weight: bold;
+    font-style: italic;
+    color: gray;
+}
+
+.parameter-key .name {
+	font-size: 14px;
+}
+
+.parameter-key .name.required {
+    font-weight: bold;
+}
+
+.parameter-key .requiredlabel {
+	font-size: 10px;
+    color: rgba(255,0,0,.6);    
+    font-weight: bold;
+}
+
+.parameter-key .type {
+    font-size: 12px;
+    padding: 5px 0;
+    font-family: monospace;
+    font-weight: bold;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Examples
+ ----------------------------------------------------------------------------------------------------------*/
+ 
+.op-block-contents .example-select {
+    margin: 10px 0 5px 0;
+	border-width: 1px;
+	font-weight:bold;
+    padding: 5px 40px 5px 10px;
+    border: 1px solid #41444e;
+    border-radius: 4px;
+    box-shadow: 0 1px 2px 0 rgba(0,0,0,.25);
+    background: hsla(0,0%,100%,.3);
+}
+
+.op-block-contents .example-select:disabled {
+    color: rgba(0,0,0,.50);
+    border: 1px solid rgba(0,0,0,.50);
+}
+
+.op-block-contents .example {
+    margin: 0;
+    padding: 5px 20px;
+    white-space: pre-wrap;
+    word-wrap: break-word;
+    hyphens: auto;
+    border-radius: 4px;
+    background: #41444e;
+    overflow-wrap: break-word;
+    font-family: monospace;
+    font-weight: 400;
+    color: #fff;
+	display: none;
+	max-width: 800px;
+	max-height: 800px;
+	text-overflow: auto;
+}
+
+.op-block-contents .example.active {
+	display:block;
+}
+
+.op-block-contents .model {
+	display: none;
+}
+
+.op-block-contents .model.active {
+	display:block;
+}
+
+/*-----------------------------------------------------------------------------------------------------------
+ - Headers
+ ----------------------------------------------------------------------------------------------------------*/
+
+.section {
+    font-weight: bold;
+    padding: 5px 0;
+    text-align: left;
+}
+
+.headers .name {
+    padding: 5px 0;
+    font-family: monospace;
+    font-weight: bold;
+}
+
+div.headers {
+	margin: 20px 0px;
+}
+
+.headers .type {
+    padding: 5px 0;
+    font-family: monospace;
+    font-weight: bold;
+}
+
+.section-name {
+	display: inline-block;
+	vertical-align: top;
+	margin-right: 20px;
+    font-weight: bold;
+    padding: 5px 0;
+    text-align: left;
+}
+
+.section-table {
+	display: inline-block;
+}
+
+.responses .section-table td {
+	padding: 5px 20px 5px 0px;
+	text-align: left;
+    border-bottom: 1px solid rgba(59,65,81,.2);
+}
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/dark.css b/juneau-microservice/juneau-microservice-template/files/htdocs/themes/dark.css
similarity index 100%
rename from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/dark.css
rename to juneau-microservice/juneau-microservice-template/files/htdocs/themes/dark.css
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/devops.css b/juneau-microservice/juneau-microservice-template/files/htdocs/themes/devops.css
similarity index 100%
copy from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/devops.css
copy to juneau-microservice/juneau-microservice-template/files/htdocs/themes/devops.css
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/light.css b/juneau-microservice/juneau-microservice-template/files/htdocs/themes/light.css
similarity index 100%
rename from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/light.css
rename to juneau-microservice/juneau-microservice-template/files/htdocs/themes/light.css
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/original.css b/juneau-microservice/juneau-microservice-template/files/htdocs/themes/original.css
similarity index 100%
rename from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/original.css
rename to juneau-microservice/juneau-microservice-template/files/htdocs/themes/original.css
diff --git a/juneau-microservice/juneau-microservice-template/jetty.xml b/juneau-microservice/juneau-microservice-template/files/jetty.xml
similarity index 100%
rename from juneau-microservice/juneau-microservice-template/jetty.xml
rename to juneau-microservice/juneau-microservice-template/files/jetty.xml
diff --git a/juneau-microservice/juneau-microservice-template/my-microservice.cfg b/juneau-microservice/juneau-microservice-template/my-microservice.cfg
index c6e4d05..3c8aea5 100755
--- a/juneau-microservice/juneau-microservice-template/my-microservice.cfg
+++ b/juneau-microservice/juneau-microservice-template/my-microservice.cfg
@@ -29,7 +29,7 @@ saveConfigAction = RESTART_SERVER
 [Jetty]
 
 # Path of the jetty.xml file used to configure the Jetty server.
-config = jetty.xml
+config = files/jetty.xml
 
 # Resolve Juneau variables in the jetty.xml file.
 resolveVars = true
@@ -45,12 +45,19 @@ port = 10000,0,0,0
 #=======================================================================================================================
 [REST]
 
+staticFiles = htdocs:files/htdocs
+
 # Stylesheet to use for HTML views.
-# The default options are:
-#  - servlet:/styles/juneau.css
-#  - servlet:/styles/devops.css
-# Other stylesheets can be referenced relative to the servlet package or working directory.
-stylesheet = servlet:/styles/devops.css
+theme = servlet:/htdocs/themes/devops.css
+
+headerIcon = servlet:/htdocs/images/juneau.png
+headerLink = http://juneau.apache.org
+footerIcon = servlet:/htdocs/images/asf.png
+footerLink = http://www.apache.org
+
+icon = $C{REST/headerIcon}
+header = <a href='$U{$C{REST/headerLink}}'><img src='$U{$C{REST/headerIcon}}' style='position:absolute;top:5;right:5;background-color:transparent;height:30px'/></a>
+footer = <a href='$U{$C{REST/footerLink}}'><img style='float:right;padding-right:20px;height:32px' src='$U{$C{REST/footerIcon}}'>
 
 #=======================================================================================================================
 # Console settings
diff --git a/juneau-microservice/juneau-microservice-template/src/assembly/bin.xml b/juneau-microservice/juneau-microservice-template/src/assembly/bin.xml
index 005fdfd..1c4f696 100644
--- a/juneau-microservice/juneau-microservice-template/src/assembly/bin.xml
+++ b/juneau-microservice/juneau-microservice-template/src/assembly/bin.xml
@@ -35,6 +35,7 @@
 				<include>src/main/**</include>
 				<include>src/test/**</include>
 				<include>.settings/**</include>
+				<include>files/**</include>
 				<include>META-INF/**</include>
 				<include>jetty.xml</include>
 				<include>my-microservice.cfg</include>
diff --git a/juneau-microservice/juneau-microservice-template/src/main/java/org/apache/juneau/microservice/sample/RootResources.java b/juneau-microservice/juneau-microservice-template/src/main/java/org/apache/juneau/microservice/sample/RootResources.java
index f0092d9..c96b89d 100755
--- a/juneau-microservice/juneau-microservice-template/src/main/java/org/apache/juneau/microservice/sample/RootResources.java
+++ b/juneau-microservice/juneau-microservice-template/src/main/java/org/apache/juneau/microservice/sample/RootResources.java
@@ -18,7 +18,7 @@ import org.apache.juneau.rest.*;
 import org.apache.juneau.rest.annotation.HtmlDoc;
 import org.apache.juneau.rest.annotation.RestResource;
 import org.apache.juneau.rest.widget.ContentTypeMenuItem;
-import org.apache.juneau.rest.widget.StyleMenuItem;
+import org.apache.juneau.rest.widget.ThemeMenuItem;
 
 /**
  * Root microservice page.
@@ -30,7 +30,7 @@ import org.apache.juneau.rest.widget.StyleMenuItem;
 	htmldoc=@HtmlDoc(
 		widgets={
 			ContentTypeMenuItem.class,
-			StyleMenuItem.class
+			ThemeMenuItem.class
 		},
 		navlinks={
 			"options: servlet:/?method=OPTIONS"
diff --git a/juneau-microservice/juneau-microservice-test/jetty.xml b/juneau-microservice/juneau-microservice-test/files/jetty.xml
similarity index 100%
rename from juneau-microservice/juneau-microservice-test/jetty.xml
rename to juneau-microservice/juneau-microservice-test/files/jetty.xml
diff --git a/juneau-microservice/juneau-microservice-test/juneau-microservice-test.cfg b/juneau-microservice/juneau-microservice-test/juneau-microservice-test.cfg
index f76dbb1..a3f5bea 100644
--- a/juneau-microservice/juneau-microservice-test/juneau-microservice-test.cfg
+++ b/juneau-microservice/juneau-microservice-test/juneau-microservice-test.cfg
@@ -14,12 +14,14 @@
 saveConfigAction = RESTART_SERVER
 
 [Jetty]
-config = jetty.xml
+config = files/jetty.xml
 resolveVars = true
 port = 10001,0,0,0
 
 [REST]
 
+staticFiles = htdocs:htdocs
+
 [Logging]
 logDir = $S{user.dir}/target/logs
 logFile = test.%g.log
diff --git a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestConfig.java b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestConfig.java
index 3ae3a7b..fdfce10 100644
--- a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestConfig.java
+++ b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestConfig.java
@@ -68,15 +68,16 @@ import org.apache.juneau.xmlschema.*;
 		header={
 			"<h1>$R{resourceTitle}</h1>",
 			"<h2>$R{methodSummary,resourceDescription}</h2>",
-			"<a href='http://juneau.apache.org'><img src='$U{servlet:/htdocs/juneau.png}' style='position:absolute;top:5;right:5;background-color:transparent;height:30px'/></a>"
+			"$C{REST/header}"
 		},
 		navlinks={
 			"up: request:/.."
 		},
-		stylesheet="$C{REST/stylesheet,servlet:/styles/devops.css}",
+		stylesheet="$C{REST/theme,servlet:/htdocs/themes/devops.css}",
 		head={
-			"<link rel='icon' href='$U{servlet:/htdocs/juneau.png}'/>"
-		}
+			"<link rel='icon' href='$U{$C{REST/icon}}'/>"
+		},
+		footer="$C{REST/footer}"
 	),
 	
 	// Optional external configuration file.
@@ -84,6 +85,6 @@ import org.apache.juneau.xmlschema.*;
 
 	// These are static files that are served up by the servlet under the specified sub-paths.
 	// For example, "/servletPath/htdocs/javadoc.css" resolves to the file "[servlet-package]/htdocs/javadoc.css"
-	staticFiles={"htdocs:htdocs","styles:styles"}
+	staticFiles={"$C{REST/staticFiles}"}
 )
 public interface BasicRestConfig {}
diff --git a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestServlet.java b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestServlet.java
index 556da39..9b7eca8 100644
--- a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestServlet.java
+++ b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicRestServlet.java
@@ -204,10 +204,6 @@ public abstract class BasicRestServlet extends RestServlet implements BasicRestC
 		summary="Swagger documentation",
 		description="Swagger documentation for this resource.",
 		htmldoc=@HtmlDoc(
-			header={
-				"<h1>$R{resourceTitle}</h1>",
-				"<h2>$R{resourceDescription}</h2>"
-			},
 			navlinks={
 				"back: servlet:/",
 				"json: servlet:/?method=OPTIONS&Accept=text/json&plainText=true"
diff --git a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ContentTypeMenuItem.java b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ContentTypeMenuItem.java
index 9582250..cf31d83 100644
--- a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ContentTypeMenuItem.java
+++ b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ContentTypeMenuItem.java
@@ -45,7 +45,7 @@ import org.apache.juneau.utils.*;
  * 				<js>"options: ..."</js>,
  * 				<js>"$W{QueryMenuItem}"</js>,
  * 				<js>"$W{ContentTypeMenuItem}"</js>,
- * 				<js>"$W{StyleMenuItem}"</js>,
+ * 				<js>"$W{ThemeMenuItem}"</js>,
  * 				<js>"source: ..."</js>
  * 			}
  * 		)
diff --git a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/PoweredByApache.java b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/PoweredByApache.java
deleted file mode 100644
index ab8ebf1..0000000
--- a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/PoweredByApache.java
+++ /dev/null
@@ -1,62 +0,0 @@
-// ***************************************************************************************************************************
-// * Licensed to the Apache Software Foundation (ASF) under one or more contributor license agreements.  See the NOTICE file *
-// * distributed with this work for additional information regarding copyright ownership.  The ASF licenses this file        *
-// * to you under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance            *
-// * with the License.  You may obtain a copy of the License at                                                              *
-// *                                                                                                                         *
-// *  http://www.apache.org/licenses/LICENSE-2.0                                                                             *
-// *                                                                                                                         *
-// * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an  *
-// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the License for the        *
-// * specific language governing permissions and limitations under the License.                                              *
-// ***************************************************************************************************************************
-package org.apache.juneau.rest.widget;
-
-import org.apache.juneau.*;
-import org.apache.juneau.rest.*;
-
-/**
- * Widget that places a powered-by-Apache message on the page.
- * 
- * <p>
- * The variable it resolves is <js>"$W{PoweredByApache}"</js>.
- * 
- * <p>
- * It produces a simple Apache icon floating on the right.
- * Typically it's used in the footer of the page, as shown below in the <code>RootResources</code> from the examples:
- * 
- * <p class='bcode'>
- * 	<ja>@RestResource</ja>(
- * 		path=<js>"/"</js>,
- * 		title=<js>"Root resources"</js>,
- * 		description=<js>"Example of a router resource page."</js>,
- * 		widgets={
- * 			PoweredByApache.<jk>class</jk>
- * 		},
- * 		htmldoc=<ja>@HtmlDoc</ja>(
- * 			footer=<js>"$W{PoweredByApache}"</js>
- * 		)
- * </p>
- * 
- * <p>
- * It renders the following image:
- * <img class='bordered' src='doc-files/PoweredByApacheWidget.png'>
- * 
- * <h5 class='section'>See Also:</h5>
- * <ul>
- * 	<li class='link'><a class="doclink" href="../../../../../overview-summary.html#juneau-rest-server.Widgets">Overview &gt; juneau-rest-server &gt; Widgets</a>
- * </ul>
- */
-public class PoweredByApache extends Widget {
-
-	/**
-	 * Returns an Apache image tag hyperlinked to <js>"http://apache.org"</js>
-	 */
-	@Override /* Widget */
-	public String getHtml(RestRequest req) throws Exception {
-		UriResolver r = req.getUriResolver();
-		return "<a href='http://apache.org'><img style='float:right;padding-right:20px;height:32px' src='"+r.resolve("servlet:/htdocs/asf.png")+"'>";
-	}
-}
-
-
diff --git a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/QueryMenuItem.java b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/QueryMenuItem.java
index dc0bda4..e5894ae 100644
--- a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/QueryMenuItem.java
+++ b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/QueryMenuItem.java
@@ -42,7 +42,7 @@ import org.apache.juneau.rest.converters.*;
  * 				<js>"options: ..."</js>,
  * 				<js>"$W{QueryMenuItem}"</js>,
  * 				<js>"$W{ContentTypeMenuItem}"</js>,
- * 				<js>"$W{StyleMenuItem}"</js>,
+ * 				<js>"$W{ThemeMenuItem}"</js>,
  * 				<js>"source: ..."</js>
  * 			}
  * 		),
diff --git a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/StyleMenuItem.java b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ThemeMenuItem.java
similarity index 92%
rename from juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/StyleMenuItem.java
rename to juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ThemeMenuItem.java
index de20d66..1be82db 100644
--- a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/StyleMenuItem.java
+++ b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/widget/ThemeMenuItem.java
@@ -22,7 +22,7 @@ import org.apache.juneau.utils.*;
  * Widget that returns back a list of hyperlinks for rendering the contents of a page in the various default styles.
  * 
  * <p>
- * The variable it resolves is <js>"$W{StyleMenuItem}"</js>.
+ * The variable it resolves is <js>"$W{ThemeMenuItem}"</js>.
  * 
  * <p>
  * An example of this widget can be found in the <code>PetStoreResource</code> in the examples that provides
@@ -32,7 +32,7 @@ import org.apache.juneau.utils.*;
  * 		name=<jsf>GET</jsf>,
  * 		path=<js>"/"</js>,
  * 		widgets={
- * 			StyleMenuItem.<jk>class</jk>,
+ * 			ThemeMenuItem.<jk>class</jk>,
  * 		},
  * 		htmldoc=<ja>@HtmlDoc</ja>(
  * 			navlinks={
@@ -40,7 +40,7 @@ import org.apache.juneau.utils.*;
  * 				<js>"options: ..."</js>,
  * 				<js>"$W{QueryMenuItem}"</js>,
  * 				<js>"$W{ContentTypeMenuItem}"</js>,
- * 				<js>"$W{StyleMenuItem}"</js>,
+ * 				<js>"$W{ThemeMenuItem}"</js>,
  * 				<js>"source: ..."</js>
  * 			}
  * 		)
@@ -53,13 +53,13 @@ import org.apache.juneau.utils.*;
  * 	<li class='link'><a class="doclink" href="../../../../../overview-summary.html#juneau-rest-server.Widgets">Overview &gt; juneau-rest-server &gt; Widgets</a>
  * </ul>
  */
-public class StyleMenuItem extends MenuItemWidget {
+public class ThemeMenuItem extends MenuItemWidget {
 
 	private static final String[] BUILT_IN_STYLES = {"devops", "light", "original", "dark"};
 
 	@Override /* Widget */
 	public String getLabel(RestRequest req) {
-		return "styles";
+		return "themes";
 	}
 	/**
 	 * Looks at the supported media types from the request and constructs a list of hyperlinks to render the data
@@ -69,7 +69,7 @@ public class StyleMenuItem extends MenuItemWidget {
 	public Div getContent(RestRequest req) throws Exception {
 		Div div = div();
 		for (String s : BUILT_IN_STYLES) {
-			java.net.URI uri = req.getUri(true, new AMap<String,String>().append("stylesheet", "styles/"+s+".css"));
+			java.net.URI uri = req.getUri(true, new AMap<String,String>().append("stylesheet", "htdocs/themes/"+s+".css"));
 			div.children(a(uri, s), br());
 		}
 		return div;
diff --git a/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/devops.css b/juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/themes/devops.css
similarity index 100%
rename from juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/styles/devops.css
rename to juneau-rest/juneau-rest-server/src/main/resources/org/apache/juneau/rest/htdocs/themes/devops.css

-- 
To stop receiving notification emails like this one, please contact
jamesbognar@apache.org.