Skip to content

Commit

Permalink
Chore: Bump Textual to 0.72.0 (and other deps too) (#599)
Browse files Browse the repository at this point in the history
* chore: bump version, fix footer

* fix: update snapshots, improve insert_buffer to prevent resize

* fix: use published textual-textarea pkg

* fix: update bad snapshot for test_toggle_sidebar

* fix: add new snapshots for tx bar test

* chore: bump tomlkit, importlib_metadata

* chore: remove numpy pin

* chore: bulk update other packages; fix issue with new theme

* fix: set code editor height to zero before it is mounted

* fix: pin to duckdb 1.0 for tests

* fix: add back numpy pin
  • Loading branch information
tconbeer authored Jul 10, 2024
1 parent 106540b commit 7cc55b2
Show file tree
Hide file tree
Showing 30 changed files with 10,483 additions and 10,409 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/static.yml
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,6 @@ jobs:
- name: Run analysis
run: |
poetry run black . --check
poetry run ruff format .
poetry run ruff check .
poetry run mypy
11 changes: 4 additions & 7 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -1,11 +1,8 @@
repos:
- repo: https://github.com/psf/black
rev: 24.3.0
hooks:
- id: black
- repo: https://github.com/astral-sh/ruff-pre-commit
rev: v0.3.7
rev: v0.5.1
hooks:
- id: ruff-format
- id: ruff
args: [ --fix, --exit-non-zero-on-fix ]
- repo: https://github.com/pre-commit/mirrors-mypy
Expand All @@ -16,8 +13,8 @@ repos:
- click
- duckdb>=0.8.0
- shandy-sqlfmt[jinjafmt]
- textual>=0.60.1
- textual-textarea>=0.13.1
- textual>=0.72.0
- textual-textarea>=0.14.0
- textual-fastdatatable>=0.7.1
- pytest
- types-pygments
Expand Down
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,18 @@ All notable changes to this project will be documented in this file.

## [Unreleased]

### Features

- Harlequin now supports an additional [theme](https://harlequin.sh/docs/themes), [`coffee`](https://pygments.org/styles/#coffee).

### Changes

- Harlequin's Footer has been re-designed. In the footer, `CTRL+` key presses are now represented by a carat, `^`. For example, instead of `CTRL+Q Quit` the footer now reads `^q Quit`.

### Bug Fixes

- Fixed a bug where the main panel would resize while the code editor was being mounted at app start-up.

## [1.22.2] - 2024-07-09

### Bug Fixes
Expand Down
4 changes: 2 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
.PHONY: check
check:
black .
ruff format .
ruff check . --fix
pytest -m "not online"
mypy

.PHONY: lint
lint:
black .
ruff format .
ruff check . --fix
mypy

Expand Down
1,305 changes: 652 additions & 653 deletions poetry.lock

Large diffs are not rendered by default.

36 changes: 18 additions & 18 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,9 @@ build-backend = "poetry.core.masonry.api"
python = ">=3.8.1,<4.0.0"

# textual and component libraries
textual = "==0.60.1"
textual = "==0.72.0"
textual-fastdatatable = "==0.7.1"
textual-textarea = "==0.13.1"
textual-textarea = "==0.14.0"

# click
click = "^8.1.3"
Expand All @@ -34,29 +34,30 @@ rich-click = "^1.7.1"
duckdb = ">=0.8.0"
shandy-sqlfmt = ">=0.19.0"
platformdirs = ">=3.10,<5.0"
importlib_metadata = { version = ">=4.6.0", python = "<3.10.0" }
tomlkit = "^0.12.3"
importlib_metadata = { version = ">=8.0", python = "<3.10.0" }
tomlkit = "^0.12.5"
questionary = "^2.0.1"

# optional deps
boto3 = { version = "^1.34.22", optional = true }

# temporary pins
# pin numpy to fix compatibility between pyarrow (textual-fastdatatable)
# and harlequin-databricks. Should be able to remove when harlequin-databricks
# dependency on databricks-sql-connector gets updated
# pin numpy to fix PEP-517 build-backend compatibility issues stemming
# from the removal of distutils in python 3.12+
# https://stackoverflow.com/questions/77582651/why-doesnt-numpy-support-pep517-builds
numpy = [
{ version = "<1.25.0,>=1.21.0", python = ">=3.8.0,<3.9.0"},
{ version = "<2.0.0,>=1.21.0", python = ">=3.9.0,<3.13.0"}
{ version = "<2.0.0,>=1.21.0", python = ">=3.9.0,<3.12.0"},
{ version = "<2.0.0,>=1.26.0", python = ">=3.12.0,<3.13.0"},
]

# optional deps
boto3 = { version = "^1.34.22", optional = true }

# database adapters (optional installs for extras)
harlequin-postgres = { version = "^0.2", optional = true }
harlequin-mysql = { version = "^0.1", optional = true }
harlequin-odbc = { version = "^0.1", optional = true }
harlequin-bigquery = { version = "^1.0", optional = true }
harlequin-trino = { version = "^0.1", optional = true }
harlequin-databricks = { version = "^0.1", python = ">=3.9.0", optional = true }
harlequin-databricks = { version = "^0.3", python = ">=3.9.0", optional = true }
harlequin-adbc = { version = "^0.1", python = ">=3.9.0", optional = true }
harlequin-cassandra = { version = "^0.1", python = ">=3.9.0", optional = true }
harlequin-nebulagraph = { version = "^0.1", python = ">=3.9.0", optional = true }
Expand All @@ -69,9 +70,8 @@ harlequin-mysql = "^0.1.1"
pyinstrument = "^4.6.2"

[tool.poetry.group.static.dependencies]
black = ">=23.3,<25.0"
ruff = ">=0.0.285"
mypy = "^1.2.0"
ruff = "^0.5"
mypy = "^1.10.0"
types-pygments = "^2.16.0.0"
pandas-stubs = "^2"
boto3-stubs = "^1.34.23"
Expand All @@ -80,8 +80,8 @@ boto3-stubs = "^1.34.23"
pytest = ">=7.3.1,<9.0.0"
pytest-asyncio = "^0.21.0"
pytest-textual-snapshot = { git = "https://github.com/tconbeer/pytest-textual-snapshot.git", branch = "main" }
# extension tests require earlier version of duckdb.
duckdb = "^0.10"
# extension tests require consistent version of duckdb.
duckdb = "1.0.0"

[tool.poetry.scripts]
harlequin = "harlequin.cli:harlequin"
Expand Down Expand Up @@ -120,7 +120,7 @@ files = [
"src/**/*.py",
"tests/**/*.py",
]
mypy_path = "stubs"
mypy_path = "stubs,src"

show_column_numbers = true

Expand Down
5 changes: 4 additions & 1 deletion src/harlequin/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,8 @@
from harlequin.transaction_mode import HarlequinTransactionMode

if TYPE_CHECKING:
from textual.await_complete import AwaitComplete

from harlequin.keymap import HarlequinKeyMap


Expand Down Expand Up @@ -209,6 +211,7 @@ def compose(self) -> ComposeResult:
self.editor_collection = EditorCollection(
language="sql", theme=self.theme, classes="hide-tabs"
)
self.editor_collection.add_class("premount")
self.editor: CodeEditor | None = None
editor_placeholder = Lazy(widget=self.editor_collection)
editor_placeholder.border_title = self.editor_collection.border_title
Expand Down Expand Up @@ -245,7 +248,7 @@ def push_screen( # type: ignore
wait_for_dismiss=wait_for_dismiss,
)

def pop_screen(self) -> Screen[object]:
def pop_screen(self) -> "AwaitComplete":
new_screen = super().pop_screen()
if (
len(self.screen_stack) == 1
Expand Down
13 changes: 10 additions & 3 deletions src/harlequin/app.tcss
Original file line number Diff line number Diff line change
Expand Up @@ -89,11 +89,19 @@ DataCatalog * .directory-tree--hidden {
width: 3fr;
}

CodeEditor,
EditorCollection {
height: 1fr;
width: 100%;
}
EditorCollection.premount {
height: 0;
border: none;
}

CodeEditor {
height: 100%;
width: 100%;
}

CompletionList {
background: $background-lighten-2 ;
Expand Down Expand Up @@ -247,8 +255,7 @@ RunQueryBar.non-responsive Input {
}

/* RESULTS VIEWER */

TabbedContent,
ResultsViewer,
TabPane {
height: 1fr;
width: 1fr;
Expand Down
30 changes: 17 additions & 13 deletions src/harlequin/app_base.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,10 @@
from typing import Type, Union

from textual.app import App
from textual.binding import Binding
from textual.binding import ActiveBinding
from textual.css.stylesheet import Stylesheet
from textual.dom import DOMNode
from textual.driver import Driver
from textual.screen import Screen
from textual.types import CSSPathType

from harlequin.colors import HarlequinColors
Expand All @@ -16,6 +16,18 @@
)


class ScreenBase(Screen):
@property
def active_bindings(self) -> dict[str, ActiveBinding]:
def sort_key(binding_pair: tuple[str, ActiveBinding]) -> int:
return 0 if binding_pair[1].node == self.app else 1

binding_map = {
k: v for k, v in sorted(super().active_bindings.items(), key=sort_key)
}
return binding_map


class AppBase(App, inherit_bindings=False):
"""
A common base app for Harlequin and its mini-apps.
Expand All @@ -39,16 +51,8 @@ def __init__(
self.design = self.app_colors.design_system
self.stylesheet = Stylesheet(variables=self.get_css_variables())

@property
def namespace_bindings(self) -> dict[str, tuple[DOMNode, Binding]]:
def get_default_screen(self) -> Screen:
"""
Re-order bindings so they appear in the footer with the global bindings first.
Changes the default screen to re-order bindings, with global bindings first.
"""

def sort_key(item: tuple[str, tuple[DOMNode, Binding]]) -> int:
return 0 if item[1][0] == self else 1

binding_map = {
k: v for k, v in sorted(super().namespace_bindings.items(), key=sort_key)
}
return binding_map
return ScreenBase(id="_default")
3 changes: 1 addition & 2 deletions src/harlequin/cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -306,8 +306,7 @@ def inner_cli(
params = list(kwargs.keys())
for k in params:
if (
ctx.get_parameter_source(k)
== click.core.ParameterSource.DEFAULT # type: ignore[attr-defined]
ctx.get_parameter_source(k) == click.core.ParameterSource.DEFAULT # type: ignore[attr-defined]
):
kwargs.pop(k)
# conn_str is an arg, not an option, so get_paramter_source is always CLI
Expand Down
5 changes: 4 additions & 1 deletion src/harlequin/colors.py
Original file line number Diff line number Diff line change
Expand Up @@ -187,7 +187,10 @@ def from_theme(cls, theme: str) -> "HarlequinColors":
prop_name: [
extract_color(style.styles.get(token_type, ""))
for token_type in token_type_list
if extract_color(style.styles.get(token_type, ""))
if (
extract_color(style.styles.get(token_type, ""))
and extract_color(style.styles.get(token_type, "")) != background
)
]
for prop_name, token_type_list in cls.MAPPING.items()
}
Expand Down
14 changes: 7 additions & 7 deletions src/harlequin/components/code_editor.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from textual.css.query import NoMatches
from textual.message import Message
from textual.widgets import ContentSwitcher, TabbedContent, TabPane, Tabs
from textual.widgets.text_area import Selection
from textual_textarea import TextAreaSaved, TextEditor

from harlequin.autocomplete import MemberCompleter, WordCompleter
Expand All @@ -18,7 +19,6 @@


class CodeEditor(TextEditor, inherit_bindings=False):

class Submitted(Message, bubble=True):
"""Posted when user runs the query.
Expand Down Expand Up @@ -131,7 +131,6 @@ def _semicolons(self) -> list[tuple[int, int]]:


class EditorCollection(TabbedContent):

BORDER_TITLE = "Query Editor"

class EditorSwitched(Message):
Expand Down Expand Up @@ -163,6 +162,7 @@ def __init__(
self.counter = 0
self._word_completer: WordCompleter | None = None
self._member_completer: MemberCompleter | None = None
self.startup_cache = load_cache()

@property
def current_editor(self) -> CodeEditor:
Expand Down Expand Up @@ -208,9 +208,8 @@ def word_completer(self, new_completer: WordCompleter) -> None:
pass

async def on_mount(self) -> None:
cache = load_cache()
if cache is not None:
for _i, buffer in enumerate(cache.buffers):
if self.startup_cache is not None:
for _i, buffer in enumerate(self.startup_cache.buffers):
await self.action_new_buffer(state=buffer)
# we can't load the focus state here, since Tabs
# really wants to activate the first tab when it's
Expand All @@ -220,6 +219,7 @@ async def on_mount(self) -> None:
self.query_one(Tabs).can_focus = False
self.current_editor.word_completer = self.word_completer
self.current_editor.member_completer = self.member_completer
self.remove_class("premount")
self.post_message(WidgetMounted(widget=self))

def on_focus(self) -> None:
Expand All @@ -235,8 +235,8 @@ def on_tabbed_content_tab_activated(
self.current_editor.focus()

async def insert_buffer_with_text(self, query_text: str) -> None:
new_editor = await self.action_new_buffer()
new_editor.text = query_text
state = BufferState(selection=Selection(), text=query_text)
new_editor = await self.action_new_buffer(state=state)
new_editor.focus()

async def action_new_buffer(
Expand Down
4 changes: 0 additions & 4 deletions src/harlequin/components/data_catalog.py
Original file line number Diff line number Diff line change
Expand Up @@ -184,13 +184,11 @@ def action_focus_query_editor(self) -> None:


class HarlequinTree(Tree, inherit_bindings=False):

double_click: int | None = None

async def on_click(self, event: Click) -> None:
meta = event.style.meta
click_line: Union[int, None] = meta.get("line", None)
self.log(meta, click_line, self.double_click)
if (
self.double_click is not None
and click_line is not None
Expand Down Expand Up @@ -448,15 +446,13 @@ def _reload_objects(self) -> None:
else:
buckets = [s3.Bucket(self.bucket)]
for bucket in buckets:
self.log(f"building tree for {bucket.name}")
data[bucket.name] = recursive_dict()
object_gen = (
bucket.objects.filter(Prefix=self.prefix)
if self.prefix
else bucket.objects.all()
)
for obj in object_gen:
self.log(f"inserting {obj.key} into tree {bucket.name}")
key_parts = obj.key.split("/")
target = data[bucket.name]
for part in key_parts:
Expand Down
1 change: 0 additions & 1 deletion src/harlequin/components/history_screen.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@ class HistoryList(OptionList):


class HistoryScreen(Screen[str]):

def __init__(
self,
history: History,
Expand Down
1 change: 0 additions & 1 deletion src/harlequin/components/results_viewer.py
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,6 @@ def get_visible_table(self) -> Union[ResultsTable, None]:
try:
return tables.first(ResultsTable)
except NoMatches:
self.log("NO TABLES FOUND")
return None

async def push_table(
Expand Down
Loading

0 comments on commit 7cc55b2

Please sign in to comment.