Skip to content

[SPARK-24490][WebUI] Use WebUI.addStaticHandler in web UIs #21510

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ class HistoryServer(

attachHandler(ApiRootResource.getServletHandler(this))

attachHandler(createStaticHandler(SparkUI.STATIC_RESOURCE_DIR, "/static"))
addStaticHandler(SparkUI.STATIC_RESOURCE_DIR)

val contextHandler = new ServletContextHandler
contextHandler.setContextPath(HistoryServer.UI_PATH_PREFIX)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ class MasterWebUI(
val masterPage = new MasterPage(this)
attachPage(new ApplicationPage(this))
attachPage(masterPage)
attachHandler(createStaticHandler(MasterWebUI.STATIC_RESOURCE_DIR, "/static"))
addStaticHandler(MasterWebUI.STATIC_RESOURCE_DIR)
attachHandler(createRedirectHandler(
"/app/kill", "/", masterPage.handleAppKillRequest, httpMethods = Set("POST")))
attachHandler(createRedirectHandler(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ class WorkerWebUI(
val logPage = new LogPage(this)
attachPage(logPage)
attachPage(new WorkerPage(this))
attachHandler(createStaticHandler(WorkerWebUI.STATIC_RESOURCE_BASE, "/static"))
addStaticHandler(WorkerWebUI.STATIC_RESOURCE_BASE)
attachHandler(createServletHandler("/log",
(request: HttpServletRequest) => logPage.renderLog(request),
worker.securityMgr,
Expand Down
2 changes: 1 addition & 1 deletion core/src/main/scala/org/apache/spark/ui/SparkUI.scala
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ private[spark] class SparkUI private (
attachTab(new StorageTab(this, store))
attachTab(new EnvironmentTab(this, store))
attachTab(new ExecutorsTab(this))
attachHandler(createStaticHandler(SparkUI.STATIC_RESOURCE_DIR, "/static"))
addStaticHandler(SparkUI.STATIC_RESOURCE_DIR)
attachHandler(createRedirectHandler("/", "/jobs/", basePath = basePath))
attachHandler(ApiRootResource.getServletHandler(this))

Expand Down
52 changes: 27 additions & 25 deletions core/src/main/scala/org/apache/spark/ui/WebUI.scala
Original file line number Diff line number Diff line change
Expand Up @@ -60,23 +60,25 @@ private[spark] abstract class WebUI(
def getHandlers: Seq[ServletContextHandler] = handlers
def getSecurityManager: SecurityManager = securityManager

/** Attach a tab to this UI, along with all of its attached pages. */
def attachTab(tab: WebUITab) {
/** Attaches a tab to this UI, along with all of its attached pages. */
def attachTab(tab: WebUITab): Unit = {
tab.pages.foreach(attachPage)
tabs += tab
}

def detachTab(tab: WebUITab) {
/** Detaches a tab from this UI, along with all of its attached pages. */
def detachTab(tab: WebUITab): Unit = {
tab.pages.foreach(detachPage)
tabs -= tab
}

def detachPage(page: WebUIPage) {
/** Detaches a page from this UI, along with all of its attached handlers. */
def detachPage(page: WebUIPage): Unit = {
pageToHandlers.remove(page).foreach(_.foreach(detachHandler))
}

/** Attach a page to this UI. */
def attachPage(page: WebUIPage) {
/** Attaches a page to this UI. */
def attachPage(page: WebUIPage): Unit = {
val pagePath = "/" + page.prefix
val renderHandler = createServletHandler(pagePath,
(request: HttpServletRequest) => page.render(request), securityManager, conf, basePath)
Expand All @@ -88,41 +90,41 @@ private[spark] abstract class WebUI(
handlers += renderHandler
}

/** Attach a handler to this UI. */
def attachHandler(handler: ServletContextHandler) {
/** Attaches a handler to this UI. */
def attachHandler(handler: ServletContextHandler): Unit = {
handlers += handler
serverInfo.foreach(_.addHandler(handler))
}

/** Detach a handler from this UI. */
def detachHandler(handler: ServletContextHandler) {
/** Detaches a handler from this UI. */
def detachHandler(handler: ServletContextHandler): Unit = {
handlers -= handler
serverInfo.foreach(_.removeHandler(handler))
}

/**
* Add a handler for static content.
* Detaches the content handler at `path` URI.
*
* @param resourceBase Root of where to find resources to serve.
* @param path Path in UI where to mount the resources.
* @param path Path in UI to unmount.
*/
def addStaticHandler(resourceBase: String, path: String): Unit = {
attachHandler(JettyUtils.createStaticHandler(resourceBase, path))
def detachHandler(path: String): Unit = {
handlers.find(_.getContextPath() == path).foreach(detachHandler)
}

/**
* Remove a static content handler.
* Adds a handler for static content.
*
* @param path Path in UI to unmount.
* @param resourceBase Root of where to find resources to serve.
* @param path Path in UI where to mount the resources.
*/
def removeStaticHandler(path: String): Unit = {
handlers.find(_.getContextPath() == path).foreach(detachHandler)
def addStaticHandler(resourceBase: String, path: String = "/static"): Unit = {
attachHandler(JettyUtils.createStaticHandler(resourceBase, path))
}

/** Initialize all components of the server. */
/** A hook to initialize components of the UI */
def initialize(): Unit

/** Bind to the HTTP server behind this web interface. */
/** Binds to the HTTP server behind this web interface. */
def bind(): Unit = {
assert(serverInfo.isEmpty, s"Attempted to bind $className more than once!")
try {
Expand All @@ -136,17 +138,17 @@ private[spark] abstract class WebUI(
}
}

/** Return the url of web interface. Only valid after bind(). */
/** @return The url of web interface. Only valid after [[bind]]. */
def webUrl: String = s"http://$publicHostName:$boundPort"

/** Return the actual port to which this server is bound. Only valid after bind(). */
/** @return The actual port to which this server is bound. Only valid after [[bind]]. */
def boundPort: Int = serverInfo.map(_.boundPort).getOrElse(-1)

/** Stop the server behind this web interface. Only valid after bind(). */
/** Stops the server behind this web interface. Only valid after [[bind]]. */
def stop(): Unit = {
assert(serverInfo.isDefined,
s"Attempted to stop $className before binding to a server!")
serverInfo.get.stop()
serverInfo.foreach(_.stop())
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ private[spark] class MesosClusterUI(
override def initialize() {
attachPage(new MesosClusterPage(this))
attachPage(new DriverPage(this))
attachHandler(createStaticHandler(MesosClusterUI.STATIC_RESOURCE_DIR, "/static"))
addStaticHandler(MesosClusterUI.STATIC_RESOURCE_DIR)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ private[spark] class StreamingTab(val ssc: StreamingContext)

def detach() {
getSparkUI(ssc).detachTab(this)
getSparkUI(ssc).removeStaticHandler("/static/streaming")
getSparkUI(ssc).detachHandler("/static/streaming")
}
}

Expand Down