# Jupyter Extensions
The debugger and query visualizer are installable Jupyter extensions.
## Installation
You must install these features before using them.
To install (one time operation), run ``tql install-extensions`` in a terminal. Installation takes several minutes.
After installation is complete, restart the Jupyter service and refresh Jupyter browser tabs.
## Debugger
The debugger extension provides an [Expression-Language](expression-language)-aware inline code editor.
The editor provides many of the features associated with an IDE-style code editor, including function completion,
syntax coloring, and real-time expression validation. In addition, the expression can be tested against timeline data,
and the expression can also be evaluated step-by-step.
Copy your expression out of the editor when you are satisfied with the result.
Expressions developed in the editor are not saved.
A known bug causes the debugger not to work when markdown cells are in the same notebook
as the debugger in Jupyter Labs. The debugger works with markdown cells in Jupyter Notebooks.
This feature is for use in Jupyter Labs and Jupyter Notebooks.
The extensions will not work in IDEs like PyCharm or VSCode.
### The debugger extension will be displayed with the current expression value:
### Hovering over a keyword will display its documentation:
### There is auto-completion for keywords, variables, and functions:
#### You can restore the expression value to the value stored in the notebook cell by right-clicking in the editor and selecting Restore Expression.
### Running Tests
To submit the expression, hit `Shift+Enter` while in the code editor, or click the button in the lower right of the debugger widget.
The results of the test will appear below the debugger:
### Code Stepper
You can "step" through the expression using the stepper/debugger. The debugger is shown by default, but if it is hidden,
right-click in the code editor and select Toggle Debug Panel to show the debugger.
From here you can run the entire expression with the debugger's play button, or set breakpoints to
stop and examine a variable at an intermediate point.
### Basic Usage
To use the debugger, see the examples below:
```python
from zeenk.tql import *
```
```python
# A limit of 10 is automatically applied to the query inside the debugger. You can override that limit
# The first column's expression in the query is shown in the query debugger/editor
# Additional columns will show in the results, but not in the editor
select("timeline.id", "'test'").from_events(1).debugger()
```
```python
# 1. Try setting breakpoints (click the open red circle) on each line that contains code
# 2. Use the step button to step over each line
# 3. Now, remove all but the last breakpoint
# 4. Use the play button to run all lines up until the last breakpoint is reached
select("""
a = 'Hello';
b = 'World!';
CONCAT(a, ' ', b)
""").from_events(1).debugger()
```
```python
test_timeline = {
'id': 'timeline_id1',
'events': [{
'id': 1,
'timestamp': 1587772800000,
'type': 'request',
'request': {
'bid': 2.0,
'impression': 1
}
}]
}
# This example uses a custom defined timeline with 1 event
select('timeline.id').from_events(1).test_timeline(test_timeline).debugger()
```
```python
# Open a debugger on project 2 with a single expression
debugger(2, 'timeline.id')
```
```python
# Open a debugger on project 2 with a single expression in a column
col("'foo'", 'the_column_name').debugger(2)
```
## Query Visualizer
The query visualizer provides a way to inspect data from a query.
Each row in the result set is an event, and they are displayed as colored shapes on the graph.
The event timestamp is used to place the events along the x-axis and metadata about the events appear on-hover.
```python
from zeenk.tql import *
select('user.*', 'bid.*', 'activity.*').from_events('lethe4').limit(100).visualize()
```
