• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1// Copyright (C) 2024 The Android Open Source Project
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7//      http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14import {raf} from '../../../core/raf_scheduler';
15import {Engine} from '../../../public';
16import {Row} from '../../../trace_processor/query_result';
17
18interface ChartConfig {
19  binAxisType?: 'nominal' | 'quantitative';
20  binAxis: 'x' | 'y';
21  countAxis: 'x' | 'y';
22  sort: string;
23  isBinned: boolean;
24  labelLimit?: number;
25}
26
27export class HistogramState {
28  private readonly sqlColumn: string;
29  private readonly engine: Engine;
30  private readonly query: string;
31
32  data?: Row[];
33  chartConfig: ChartConfig;
34
35  get isLoading() {
36    return this.data === undefined;
37  }
38
39  constructor(engine: Engine, query: string, column: string) {
40    this.engine = engine;
41    this.query = query;
42    this.sqlColumn = column;
43
44    this.chartConfig = {
45      binAxis: 'x',
46      binAxisType: 'nominal',
47      countAxis: 'y',
48      sort: 'false',
49      isBinned: true,
50      labelLimit: 500,
51    };
52
53    this.getData();
54  }
55
56  async getData() {
57    const res = await this.engine.query(`
58      SELECT ${this.sqlColumn}
59      FROM (
60        ${this.query}
61      )
62    `);
63
64    const rows: Row[] = [];
65
66    for (const it = res.iter({}); it.valid(); it.next()) {
67      const rowVal = it.get(this.sqlColumn);
68
69      if (
70        this.chartConfig.binAxisType === 'nominal' &&
71        typeof rowVal === 'bigint'
72      ) {
73        this.chartConfig.binAxisType = 'quantitative';
74      }
75
76      rows.push({
77        [this.sqlColumn]: rowVal,
78      });
79    }
80
81    this.data = rows;
82
83    if (this.chartConfig.binAxisType === 'nominal') {
84      this.chartConfig.binAxis = 'y';
85      this.chartConfig.countAxis = 'x';
86      this.chartConfig.sort = `{
87          "op": "count",
88          "order": "descending"
89        }`;
90      this.chartConfig.isBinned = false;
91    }
92
93    raf.scheduleFullRedraw();
94  }
95}
96