[SPARK-28430][UI] Fix stage table rendering when some tasks' metrics are missing
## What changes were proposed in this pull request? The Spark UI's stages table misrenders the input/output metrics columns when some tasks are missing input metrics. See the screenshot below for an example of the problem: ![image](https://user-images.githubusercontent.com/50748/61420042-a3abc100-a8b5-11e9-8a92-7986563ee712.png) This is because those columns' are defined as ```scala {if (hasInput(stage)) { metricInfo(task) { m => ... <td>....</td> } } ``` where `metricInfo` renders the node returned by the closure in case metrics are defined or returns `Nil` in case metrics are not defined. If metrics are undefined then we'll fail to render the empty `<td></td>` tag, causing columns to become misaligned as shown in the screenshot. To fix this, this patch changes this to ```scala {if (hasInput(stage)) { <td>{ metricInfo(task) { m => ... Unparsed(...) } }</td> } ``` which is an idiom that's already in use for the shuffle read / write columns. ## How was this patch tested? It isn't. I'm arguing for correctness because the modifications are consistent with rendering methods that work correctly for other columns. Closes #25183 from JoshRosen/joshrosen/fix-task-table-with-partial-io-metrics. Authored-by: Josh Rosen <rosenville@gmail.com> Signed-off-by: Dongjoon Hyun <dhyun@apple.com>
This commit is contained in:
parent
a0c2fa63ab
commit
3776fbdfde
|
@ -641,18 +641,22 @@ private[ui] class TaskPagedTable(
|
|||
<td>{accumulatorsInfo(task)}</td>
|
||||
}}
|
||||
{if (hasInput(stage)) {
|
||||
metricInfo(task) { m =>
|
||||
val bytesRead = Utils.bytesToString(m.inputMetrics.bytesRead)
|
||||
val records = m.inputMetrics.recordsRead
|
||||
<td>{bytesRead} / {records}</td>
|
||||
}
|
||||
<td>{
|
||||
metricInfo(task) { m =>
|
||||
val bytesRead = Utils.bytesToString(m.inputMetrics.bytesRead)
|
||||
val records = m.inputMetrics.recordsRead
|
||||
Unparsed(s"$bytesRead / $records")
|
||||
}
|
||||
}</td>
|
||||
}}
|
||||
{if (hasOutput(stage)) {
|
||||
metricInfo(task) { m =>
|
||||
val bytesWritten = Utils.bytesToString(m.outputMetrics.bytesWritten)
|
||||
val records = m.outputMetrics.recordsWritten
|
||||
<td>{bytesWritten} / {records}</td>
|
||||
}
|
||||
<td>{
|
||||
metricInfo(task) { m =>
|
||||
val bytesWritten = Utils.bytesToString(m.outputMetrics.bytesWritten)
|
||||
val records = m.outputMetrics.recordsWritten
|
||||
Unparsed(s"$bytesWritten / $records")
|
||||
}
|
||||
}</td>
|
||||
}}
|
||||
{if (hasShuffleRead(stage)) {
|
||||
<td class={TaskDetailsClassNames.SHUFFLE_READ_BLOCKED_TIME}>
|
||||
|
|
Loading…
Reference in a new issue