Report Builder

Overview

The RestBI Report Builder Demo App is a robust example of what can be built using the RestBI SDK. This application demonstrates how to create a dynamic and customizable reporting interface that adapts to the underlying data model. The app's flexibility and adaptability make it an excellent foundation for building interfaces tailored to specific client needs.

Key Features

  • Dynamic Interface: The app automatically adapts to the provided data model (activeModel), allowing for seamless integration with different datasets.

  • Advanced Filtering: The app supports sophisticated filtering options, enabling users to refine data queries according to various criteria.

  • Data Visualization: Query results are displayed in an interactive and customizable data grid (AgGridReact), offering a rich user experience.

How It Works

1. Setting Up the Client

The app initializes a RestBIClient to interact with the RestBI server. This client is the primary interface for executing queries and fetching data based on the selected model.

let client = new RestBIClient("http://localhost:3000");

2. Dynamic Query Builder

The interface dynamically populates based on the provided data model. In this example, the activeModelis used, but the same logic applies to any data model.

  • Column Selection: The app automatically lists all available tables and columns from the model. Users can select or deselect columns to include in the query, and the interface adjusts accordingly.

{activeModel.tables.map((table: Table) => (
  <div key={table.id}>
    <h1>{table.name}</h1>
    {table.columns.map((column: Column) => (
      <div key={column.name}>
        <Checkbox
          onChange={(e) => {
            if(e.target.checked){
              setQuery({
                ...query,
                columns: [...query.columns, column.name || '']
              })
            } else {
              setQuery({
                ...query,
                columns: query.columns.filter((col) => col !== column.name)
              })
            }
          }}
          id={column.name} name={column.name} value={column.name}/>
        <label htmlFor={column.name}>{column.name}</label>
      </div>
    ))}
  </div>
))}

This ensures that the interface is always in sync with the data model, providing a flexible foundation for building customized reporting tools.

3. Advanced Filtering

Filters are crucial for refining queries, and the app provides an intuitive way to apply them. The filtering interface is also dynamic, adjusting to the column's data type (e.g., string, number, date, boolean).

  • Dynamic Filter Options: Depending on the selected column, different operators (e.g., =, !=, LIKE, BETWEEN) and input fields are presented to the user.

<FormControl>
  <InputLabel id="operator-label">Operator</InputLabel>
  <Select labelId='operator-label' value={operator} onChange={handleOperatorChange}>
    {column.dataType === ColumnDataType.STRING && (
      <>
        <MenuItem value="=">=</MenuItem>
        <MenuItem value="!=">!=</MenuItem>
        <MenuItem value="LIKE">LIKE</MenuItem>
        <MenuItem value="IN">IN</MenuItem>
        <MenuItem value="NOT IN">NOT IN</MenuItem>
      </>
    )}
    {column.dataType === ColumnDataType.NUMBER && (
      <>
        <MenuItem value="=">=</MenuItem>
        <MenuItem value=">">{'>'}</MenuItem>
        <MenuItem value="<">{'<'}</MenuItem>
      </>
    )}
    {/* Additional conditions for DATE, BOOLEAN */}
  </Select>
</FormControl>

This approach allows for highly tailored queries, meeting various business requirements without hardcoding specific rules or filters.

4. Executing the Query

Once the query is built with the selected columns and filters, users can execute it. The app handles the query execution and updates the interface with the retrieved data.

const executeQuery = () => {
  client.executeQuery(query, activeModel).then((data) => {
    setData(data);
    setError(null);
  }).catch((err) => {
    setError(err);
  });
}

5. Displaying Results

The results are presented using AgGridReact, a flexible grid component that adapts to the structure of the data. The grid is fully interactive, allowing users to explore the results in detail.

<AgGridReact
  rowData={data.rows}
  columnDefs={data.columns.map((column) => ({ headerName: column, field: column }))}
/>

6. Error Handling

In case of errors during query execution, the app provides clear feedback to the user, including the generated SQL query. This transparency is vital for debugging and refining queries.

{error && 
  <div>
    <div className="text-red-400">Error: {error.message}</div>
    <div>Generated SQL Query: {error.query}</div>
  </div>
}

Whats Next

If you're looking to build a powerful, customizable BI tool, this demo app is a fantastic place to start. It’s designed to be flexible and user-friendly, showing just how much you can do with the RestBI SDK. Dive in, explore, and see how you can make it your own!

Once you have explored this application, check out some of the other examples.

Last updated