mirror of
https://github.com/weaveworks/scope.git
synced 2026-04-21 01:47:30 +00:00
Fixing grouped node count for filtered children nodes
Squash of: * We have to keep all the container hostnames until the end so we can count how many we've filtered * Adding tests for ContainerHostnameRenderer and PodServiceRenderer with filters * Because we filter on image name we need the image name before filtering * Alternative approach to passing decorators. * Refactor out some of the decorator capture * Don't memoise decorated calls to Render * Fixing filtered counts on containers topology Tricky, because we need the filters to be silent sometimes (when they're in the middle), but not when they're at the top, so we take the "top" filter's stats. However, this means we have to compose all user-specified filters into a single Filter layer, so we can get all stats. There are no more Silent filters, as all filters are silent (unless they are at the top). Additionally, I clarified some of the filters as their usage/terminology was inconsistent and confused. Now Filter(IsFoo, ...) *keeps* only nodes where IsFoo is true.
This commit is contained in:
@@ -12,8 +12,8 @@ type MapFunc func(report.Node, report.Networks) report.Nodes
|
||||
|
||||
// Renderer is something that can render a report to a set of Nodes.
|
||||
type Renderer interface {
|
||||
Render(report.Report) report.Nodes
|
||||
Stats(report.Report) Stats
|
||||
Render(report.Report, Decorator) report.Nodes
|
||||
Stats(report.Report, Decorator) Stats
|
||||
}
|
||||
|
||||
// Stats is the type returned by Renderer.Stats
|
||||
@@ -38,19 +38,19 @@ func MakeReduce(renderers ...Renderer) Renderer {
|
||||
}
|
||||
|
||||
// Render produces a set of Nodes given a Report.
|
||||
func (r *Reduce) Render(rpt report.Report) report.Nodes {
|
||||
func (r *Reduce) Render(rpt report.Report, dct Decorator) report.Nodes {
|
||||
result := report.Nodes{}
|
||||
for _, renderer := range *r {
|
||||
result = result.Merge(renderer.Render(rpt))
|
||||
result = result.Merge(renderer.Render(rpt, dct))
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
// Stats implements Renderer
|
||||
func (r *Reduce) Stats(rpt report.Report) Stats {
|
||||
func (r *Reduce) Stats(rpt report.Report, dct Decorator) Stats {
|
||||
var result Stats
|
||||
for _, renderer := range *r {
|
||||
result = result.merge(renderer.Stats(rpt))
|
||||
result = result.merge(renderer.Stats(rpt, dct))
|
||||
}
|
||||
return result
|
||||
}
|
||||
@@ -69,9 +69,9 @@ func MakeMap(f MapFunc, r Renderer) Renderer {
|
||||
|
||||
// Render transforms a set of Nodes produces by another Renderer.
|
||||
// using a map function
|
||||
func (m *Map) Render(rpt report.Report) report.Nodes {
|
||||
func (m *Map) Render(rpt report.Report, dct Decorator) report.Nodes {
|
||||
var (
|
||||
input = m.Renderer.Render(rpt)
|
||||
input = m.Renderer.Render(rpt, dct)
|
||||
output = report.Nodes{}
|
||||
mapped = map[string]report.IDList{} // input node ID -> output node IDs
|
||||
adjacencies = map[string]report.IDList{} // output node ID -> input node Adjacencies
|
||||
@@ -109,9 +109,45 @@ func (m *Map) Render(rpt report.Report) report.Nodes {
|
||||
}
|
||||
|
||||
// Stats implements Renderer
|
||||
func (m *Map) Stats(rpt report.Report) Stats {
|
||||
func (m *Map) Stats(_ report.Report, _ Decorator) Stats {
|
||||
// There doesn't seem to be an instance where we want stats to recurse
|
||||
// through Maps - for instance we don't want to see the number of filtered
|
||||
// processes in the container renderer.
|
||||
return Stats{}
|
||||
}
|
||||
|
||||
// Decorator transforms one renderer to another. e.g. Filters.
|
||||
type Decorator func(Renderer) Renderer
|
||||
|
||||
// ComposeDecorators composes decorators into one.
|
||||
func ComposeDecorators(decorators ...Decorator) Decorator {
|
||||
return func(r Renderer) Renderer {
|
||||
for _, decorator := range decorators {
|
||||
r = decorator(r)
|
||||
}
|
||||
return r
|
||||
}
|
||||
}
|
||||
|
||||
type applyDecorator struct {
|
||||
Renderer
|
||||
}
|
||||
|
||||
func (ad applyDecorator) Render(rpt report.Report, dct Decorator) report.Nodes {
|
||||
if dct != nil {
|
||||
return dct(ad.Renderer).Render(rpt, nil)
|
||||
}
|
||||
return ad.Renderer.Render(rpt, nil)
|
||||
}
|
||||
func (ad applyDecorator) Stats(rpt report.Report, dct Decorator) Stats {
|
||||
if dct != nil {
|
||||
return dct(ad.Renderer).Stats(rpt, nil)
|
||||
}
|
||||
return ad.Renderer.Stats(rpt, nil)
|
||||
}
|
||||
|
||||
// ApplyDecorators returns a renderer which will apply the given decorators
|
||||
// to the child render.
|
||||
func ApplyDecorators(renderer Renderer) Renderer {
|
||||
return applyDecorator{renderer}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user