Skip to content

Commit

Permalink
HParams: Add new state property to store hparam and metric filters (t…
Browse files Browse the repository at this point in the history
…ensorflow#6553)

## Motivation for features / changes
Now that the filter dialog is merged tensorflow#6493 we need to add support for
filtering by hparams. However, tensorflow#6544 changed the way hparam values are
read. This change adds a new property to state in which to store
dashboard related hparam and metric filters.

See tensorflow#6488 for the WIP integration with the runs_table_container +
tb_data_table -> common_selectors + hparam_selectors.
  • Loading branch information
rileyajones authored and yatbear committed Aug 25, 2023
1 parent a928842 commit f229893
Show file tree
Hide file tree
Showing 10 changed files with 332 additions and 7 deletions.
3 changes: 3 additions & 0 deletions tensorboard/webapp/hparams/_redux/BUILD
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ tf_ts_library(
"utils.ts",
],
deps = [
":types",
"//tensorboard/webapp/hparams:types",
],
)
Expand Down Expand Up @@ -47,6 +48,7 @@ tf_ts_library(
"hparams_actions.ts",
],
deps = [
":types",
"//tensorboard/webapp/hparams:types",
"@npm//@ngrx/store",
],
Expand Down Expand Up @@ -155,6 +157,7 @@ tf_ts_library(
":hparams_reducers",
":hparams_selectors",
":testing",
":types",
":utils",
"//tensorboard/webapp:app_state",
"//tensorboard/webapp:selectors",
Expand Down
11 changes: 11 additions & 0 deletions tensorboard/webapp/hparams/_redux/hparams_actions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import {
HparamAndMetricSpec,
SessionGroup,
} from '../types';
import {HparamFilter, MetricFilter} from './types';

export const hparamsDiscreteHparamFilterChanged = createAction(
'[Hparams] Hparams Discrete Hparam Filter Changed',
Expand Down Expand Up @@ -62,3 +63,13 @@ export const hparamsFetchSessionGroupsSucceeded = createAction(
sessionGroups: SessionGroup[];
}>()
);

export const dashboardHparamFilterAdded = createAction(
'[Hparams] Dashboard Hparam Filter Added',
props<{name: string; filter: HparamFilter}>()
);

export const dashboardMetricFilterAdded = createAction(
'[Hparams] Dashboard Metric Filter Added',
props<{name: string; filter: MetricFilter}>()
);
28 changes: 28 additions & 0 deletions tensorboard/webapp/hparams/_redux/hparams_reducers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,10 @@ const initialState: HparamsState = {
metrics: [],
},
dashboardSessionGroups: [],
dashboardFilters: {
hparams: new Map(),
metrics: new Map(),
},
};

const reducer: ActionReducer<HparamsState, Action> = createReducer(
Expand Down Expand Up @@ -369,6 +373,30 @@ const reducer: ActionReducer<HparamsState, Action> = createReducer(
dashboardSpecs: nextDashboardSpecs,
dashboardSessionGroups: nextDashboardSessionGroups,
};
}),
on(actions.dashboardHparamFilterAdded, (state, action) => {
const nextHparamFilters = new Map(state.dashboardFilters.hparams);
nextHparamFilters.set(action.name, action.filter);

return {
...state,
dashboardFilters: {
...state.dashboardFilters,
hparams: nextHparamFilters,
},
};
}),
on(actions.dashboardMetricFilterAdded, (state, action) => {
const nextMetricFilters = new Map(state.dashboardFilters.metrics);
nextMetricFilters.set(action.name, action.filter);

return {
...state,
dashboardFilters: {
...state.dashboardFilters,
metrics: nextMetricFilters,
},
};
})
);

Expand Down
122 changes: 122 additions & 0 deletions tensorboard/webapp/hparams/_redux/hparams_reducers_test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -630,4 +630,126 @@ describe('hparams/_redux/hparams_reducers_test', () => {
expect(state2.dashboardSessionGroups).toEqual([mockSessionGroup]);
});
});

describe('dashboardHparamFilterAdded', () => {
it('adds entry dashboardFilters', () => {
const state = buildHparamsState({
dashboardFilters: {
hparams: new Map([
[
'hparam2',
{
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: 2,
maxValue: 20,
filterLowerBound: 2,
filterUpperBound: 20,
},
],
]),
},
});
const state2 = reducers(
state,
actions.dashboardHparamFilterAdded({
name: 'hparam1',
filter: {
type: DomainType.DISCRETE,
includeUndefined: true,
filterValues: [5],
possibleValues: [5, 7, 8],
},
})
);
expect(state2.dashboardFilters).toEqual({
hparams: new Map([
[
'hparam1',
{
type: DomainType.DISCRETE,
includeUndefined: true,
filterValues: [5],
possibleValues: [5, 7, 8],
},
],
[
'hparam2',
{
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: 2,
maxValue: 20,
filterLowerBound: 2,
filterUpperBound: 20,
},
],
]),
metrics: new Map(),
});
});
});

describe('dashboardMetricFilterAdded', () => {
it('adds entry dashboardFilters', () => {
const state = buildHparamsState({
dashboardFilters: {
metrics: new Map([
[
'metric 2',
{
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: 1,
maxValue: 50,
filterLowerValue: 1,
filterUpperValue: 51,
},
],
]),
},
});
const state2 = reducers(
state,
actions.dashboardMetricFilterAdded({
name: 'metric 1',
filter: {
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: -2,
maxValue: 42,
filterLowerValue: -2,
filterUpperValue: 40,
},
})
);
expect(state2.dashboardFilters).toEqual({
hparams: new Map(),
metrics: new Map([
[
'metric 1',
{
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: -2,
maxValue: 42,
filterLowerValue: -2,
filterUpperValue: 40,
},
],
[
'metric 2',
{
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: 1,
maxValue: 50,
filterLowerValue: 1,
filterUpperValue: 51,
},
],
]),
});
});
});
});
30 changes: 29 additions & 1 deletion tensorboard/webapp/hparams/_redux/hparams_selectors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,12 @@ import {
RunToHparamsAndMetrics,
} from '../types';
import {combineHparamAndMetricSpecs} from './hparams_selectors_utils';
import {HparamsState, HPARAMS_FEATURE_KEY} from './types';
import {HparamsState, HPARAMS_FEATURE_KEY, HparamFilter} from './types';
import {
combineDefaultHparamFilters,
combineDefaultMetricFilters,
getIdFromExperimentIds,
hparamSpecToDefaultFilter,
} from './utils';

const getHparamsState =
Expand Down Expand Up @@ -232,3 +233,30 @@ export const getDashboardRunsToHparamsAndMetrics = createSelector(
return runToHparamsAndMetrics;
}
);

export const getDashboardDefaultHparamFilters = createSelector(
getDashboardHparamsAndMetricsSpecs,
(specs): Map<string, HparamFilter> => {
const hparams = new Map(
specs.hparams.map((hparamSpec) => {
return [hparamSpec.name, hparamSpecToDefaultFilter(hparamSpec)];
})
);

return hparams;
}
);

export const getDashboardHparamFilterMap = createSelector(
getHparamsState,
(state) => {
return state.dashboardFilters.hparams;
}
);

export const getDashboardMetricsFilterMap = createSelector(
getHparamsState,
(state) => {
return state.dashboardFilters.metrics;
}
);
53 changes: 53 additions & 0 deletions tensorboard/webapp/hparams/_redux/hparams_selectors_test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ See the License for the specific language governing permissions and
limitations under the License.
==============================================================================*/

import {DomainType} from '../types';
import * as selectors from './hparams_selectors';
import {
buildDiscreteFilter,
Expand Down Expand Up @@ -701,6 +702,58 @@ describe('hparams/_redux/hparams_selectors_test', () => {
});
});

describe('#getDashboardDefaultHparamFilters', () => {
it('generates default filters for all hparam specs', () => {
const state = buildStateFromHparamsState(
buildHparamsState({
dashboardSpecs: {
hparams: [
buildHparamSpec({
name: 'interval hparam',
domain: {
type: DomainType.INTERVAL,
minValue: 2,
maxValue: 5,
},
}),
buildHparamSpec({
name: 'discrete hparam',
domain: {
type: DomainType.DISCRETE,
values: [2, 4, 6, 8],
},
}),
],
},
})
);
expect(selectors.getDashboardDefaultHparamFilters(state)).toEqual(
new Map([
[
'interval hparam',
{
type: DomainType.INTERVAL,
includeUndefined: true,
minValue: 2,
maxValue: 5,
filterLowerValue: 2,
filterUpperValue: 5,
},
],
[
'discrete hparam',
{
type: DomainType.DISCRETE,
includeUndefined: true,
possibleValues: [2, 4, 6, 8],
filterValues: [2, 4, 6, 8],
},
],
])
);
});
});

it('does not use default filters when includeDefaults is false', () => {
const state = buildStateFromHparamsState(
buildHparamsState({
Expand Down
4 changes: 4 additions & 0 deletions tensorboard/webapp/hparams/_redux/testing.ts
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,10 @@ export function buildHparamsState(
metrics: overrides.dashboardSpecs?.metrics ?? [],
},
dashboardSessionGroups: overrides.dashboardSessionGroups ?? [],
dashboardFilters: {
hparams: overrides.dashboardFilters?.hparams ?? new Map(),
metrics: overrides.dashboardFilters?.metrics ?? new Map(),
},
} as HparamsState;
}

Expand Down
15 changes: 11 additions & 4 deletions tensorboard/webapp/hparams/_redux/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,14 +21,17 @@ import {
SessionGroup,
} from '../_types';

export type HparamFilter = DiscreteFilter | IntervalFilter;
export type MetricFilter = IntervalFilter;

export interface HparamsMetricsAndFilters {
hparam: {
specs: HparamSpec[];
defaultFilters: Map<string, DiscreteFilter | IntervalFilter>;
defaultFilters: Map<string, HparamFilter>;
};
metric: {
specs: MetricSpec[];
defaultFilters: Map<string, IntervalFilter>;
defaultFilters: Map<string, MetricFilter>;
};
}

Expand All @@ -47,6 +50,10 @@ export interface HparamsState {
specs: ExperimentToHparams;
dashboardSpecs: HparamAndMetricSpec;
dashboardSessionGroups: SessionGroup[];
dashboardFilters: {
hparams: Map<string, HparamFilter>;
metrics: Map<string, MetricFilter>;
};
/**
* RATIONALE: we do not use the NamespaceContextedState because of the following reasons.
* - RunsTable which uses the state renders both on the dashboard view and the
Expand All @@ -62,8 +69,8 @@ export interface HparamsState {
*/
filters: {
[id: string]: {
hparams: Map<string, DiscreteFilter | IntervalFilter>;
metrics: Map<string, IntervalFilter>;
hparams: Map<string, HparamFilter>;
metrics: Map<string, MetricFilter>;
};
};
}
Expand Down
Loading

0 comments on commit f229893

Please sign in to comment.