harlequin 2.1.2__tar.gz → 2.2.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- harlequin-2.2.0/.gitignore +181 -0
- {harlequin-2.1.2 → harlequin-2.2.0}/PKG-INFO +44 -48
- {harlequin-2.1.2 → harlequin-2.2.0}/README.md +6 -6
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/actions.py +5 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/adapter.py +26 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/app.py +52 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/app.tcss +13 -5
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/cli.py +1 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/__init__.py +2 -0
- harlequin-2.2.0/harlequin/components/debug_info.py +309 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/help_screen.py +7 -6
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/adapter.py +4 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/adapter.py +4 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_vscode/__init__.py +1 -0
- harlequin-2.2.0/pyproject.toml +173 -0
- harlequin-2.1.2/pyproject.toml +0 -153
- {harlequin-2.1.2 → harlequin-2.2.0}/LICENSE +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/__init__.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/__main__.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/app_base.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/autocomplete/__init__.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/autocomplete/completers.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/autocomplete/completion.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/autocomplete/constants.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/bindings.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/cache.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/catalog.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/catalog_cache.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/colors.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/code_editor.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/confirm_modal.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/data_catalog/__init__.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/data_catalog/database_tree.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/data_catalog/file_tree.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/data_catalog/s3_tree.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/data_catalog/tree.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/error_modal.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/export_screen.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/help_screen.md +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/history_screen.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/results_viewer.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/components/run_query_bar.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/config.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/config_wizard.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/copy_formats.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/copy_widgets.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/driver.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/editor_cache.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/exception.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/export.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/global.tcss +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/history.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/keymap.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/keys_app.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/keys_app.tcss +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/locale_manager.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/messages.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/options.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/plugins.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/py.typed +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/transaction_mode.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin/windows_timezone.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/__init__.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/catalog.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/cli_options.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/completions.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/interactions.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_duckdb/py.typed +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/__init__.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/catalog.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/cli_options.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/completions.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/interactions.py +0 -0
- {harlequin-2.1.2/src → harlequin-2.2.0}/harlequin_sqlite/py.typed +0 -0
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
*.db*
|
|
2
|
+
*.db.wal
|
|
3
|
+
*.csv
|
|
4
|
+
*.json
|
|
5
|
+
*.parquet
|
|
6
|
+
*.sql
|
|
7
|
+
*.sqlite
|
|
8
|
+
!tests/data/**/*.db
|
|
9
|
+
!tests/data/**/*.csv
|
|
10
|
+
!tests/data/**/*.json
|
|
11
|
+
!tests/data/**/*.parquet
|
|
12
|
+
!tests/data/**/*.sql
|
|
13
|
+
Pipfile
|
|
14
|
+
snapshot_report.html
|
|
15
|
+
.harlequin.toml
|
|
16
|
+
.profiles
|
|
17
|
+
|
|
18
|
+
# Byte-compiled / optimized / DLL files
|
|
19
|
+
__pycache__/
|
|
20
|
+
*.py[cod]
|
|
21
|
+
*$py.class
|
|
22
|
+
|
|
23
|
+
# C extensions
|
|
24
|
+
*.so
|
|
25
|
+
!tests/data/**/*.so
|
|
26
|
+
|
|
27
|
+
# Distribution / packaging
|
|
28
|
+
.Python
|
|
29
|
+
build/
|
|
30
|
+
develop-eggs/
|
|
31
|
+
dist/
|
|
32
|
+
downloads/
|
|
33
|
+
eggs/
|
|
34
|
+
.eggs/
|
|
35
|
+
lib/
|
|
36
|
+
lib64/
|
|
37
|
+
parts/
|
|
38
|
+
sdist/
|
|
39
|
+
var/
|
|
40
|
+
wheels/
|
|
41
|
+
share/python-wheels/
|
|
42
|
+
*.egg-info/
|
|
43
|
+
.installed.cfg
|
|
44
|
+
*.egg
|
|
45
|
+
MANIFEST
|
|
46
|
+
|
|
47
|
+
# PyInstaller
|
|
48
|
+
# Usually these files are written by a python script from a template
|
|
49
|
+
# before PyInstaller builds the exe, so as to inject date/other infos into it.
|
|
50
|
+
*.manifest
|
|
51
|
+
*.spec
|
|
52
|
+
|
|
53
|
+
# Installer logs
|
|
54
|
+
pip-log.txt
|
|
55
|
+
pip-delete-this-directory.txt
|
|
56
|
+
|
|
57
|
+
# Unit test / coverage reports
|
|
58
|
+
htmlcov/
|
|
59
|
+
.tox/
|
|
60
|
+
.nox/
|
|
61
|
+
.coverage
|
|
62
|
+
.coverage.*
|
|
63
|
+
.cache
|
|
64
|
+
nosetests.xml
|
|
65
|
+
coverage.xml
|
|
66
|
+
*.cover
|
|
67
|
+
*.py,cover
|
|
68
|
+
.hypothesis/
|
|
69
|
+
.pytest_cache/
|
|
70
|
+
cover/
|
|
71
|
+
|
|
72
|
+
# Translations
|
|
73
|
+
*.mo
|
|
74
|
+
*.pot
|
|
75
|
+
|
|
76
|
+
# Django stuff:
|
|
77
|
+
*.log
|
|
78
|
+
local_settings.py
|
|
79
|
+
db.sqlite3
|
|
80
|
+
db.sqlite3-journal
|
|
81
|
+
|
|
82
|
+
# Flask stuff:
|
|
83
|
+
instance/
|
|
84
|
+
.webassets-cache
|
|
85
|
+
|
|
86
|
+
# Scrapy stuff:
|
|
87
|
+
.scrapy
|
|
88
|
+
|
|
89
|
+
# Sphinx documentation
|
|
90
|
+
docs/_build/
|
|
91
|
+
|
|
92
|
+
# PyBuilder
|
|
93
|
+
.pybuilder/
|
|
94
|
+
target/
|
|
95
|
+
|
|
96
|
+
# Jupyter Notebook
|
|
97
|
+
.ipynb_checkpoints
|
|
98
|
+
|
|
99
|
+
# IPython
|
|
100
|
+
profile_default/
|
|
101
|
+
ipython_config.py
|
|
102
|
+
|
|
103
|
+
# pyenv
|
|
104
|
+
# For a library or package, you might want to ignore these files since the code is
|
|
105
|
+
# intended to run in multiple environments; otherwise, check them in:
|
|
106
|
+
# .python-version
|
|
107
|
+
|
|
108
|
+
# pipenv
|
|
109
|
+
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
|
|
110
|
+
# However, in case of collaboration, if having platform-specific dependencies or dependencies
|
|
111
|
+
# having no cross-platform support, pipenv may install dependencies that don't work, or not
|
|
112
|
+
# install all needed dependencies.
|
|
113
|
+
#Pipfile.lock
|
|
114
|
+
|
|
115
|
+
# poetry
|
|
116
|
+
# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
|
|
117
|
+
# This is especially recommended for binary packages to ensure reproducibility, and is more
|
|
118
|
+
# commonly ignored for libraries.
|
|
119
|
+
# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
|
|
120
|
+
#poetry.lock
|
|
121
|
+
|
|
122
|
+
# pdm
|
|
123
|
+
# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
|
|
124
|
+
#pdm.lock
|
|
125
|
+
# pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it
|
|
126
|
+
# in version control.
|
|
127
|
+
# https://pdm.fming.dev/#use-with-ide
|
|
128
|
+
.pdm.toml
|
|
129
|
+
|
|
130
|
+
# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
|
|
131
|
+
__pypackages__/
|
|
132
|
+
|
|
133
|
+
# Celery stuff
|
|
134
|
+
celerybeat-schedule
|
|
135
|
+
celerybeat.pid
|
|
136
|
+
|
|
137
|
+
# SageMath parsed files
|
|
138
|
+
*.sage.py
|
|
139
|
+
|
|
140
|
+
# Environments
|
|
141
|
+
.env
|
|
142
|
+
.venv
|
|
143
|
+
env/
|
|
144
|
+
venv/
|
|
145
|
+
ENV/
|
|
146
|
+
env.bak/
|
|
147
|
+
venv.bak/
|
|
148
|
+
|
|
149
|
+
# Spyder project settings
|
|
150
|
+
.spyderproject
|
|
151
|
+
.spyproject
|
|
152
|
+
|
|
153
|
+
# Rope project settings
|
|
154
|
+
.ropeproject
|
|
155
|
+
|
|
156
|
+
# mkdocs documentation
|
|
157
|
+
/site
|
|
158
|
+
|
|
159
|
+
# mypy
|
|
160
|
+
.mypy_cache/
|
|
161
|
+
.dmypy.json
|
|
162
|
+
dmypy.json
|
|
163
|
+
|
|
164
|
+
# ruff
|
|
165
|
+
.ruff_cache
|
|
166
|
+
|
|
167
|
+
# Pyre type checker
|
|
168
|
+
.pyre/
|
|
169
|
+
|
|
170
|
+
# pytype static type analyzer
|
|
171
|
+
.pytype/
|
|
172
|
+
|
|
173
|
+
# Cython debug symbols
|
|
174
|
+
cython_debug/
|
|
175
|
+
|
|
176
|
+
# PyCharm
|
|
177
|
+
# JetBrains specific template is maintained in a separate JetBrains.gitignore that can
|
|
178
|
+
# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
|
|
179
|
+
# and can be added to the global gitignore or merged into this file. For a more nuclear
|
|
180
|
+
# option (not recommended) you can uncomment the following to ignore the entire idea folder.
|
|
181
|
+
#.idea/
|
|
@@ -1,56 +1,53 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: harlequin
|
|
3
|
-
Version: 2.
|
|
3
|
+
Version: 2.2.0
|
|
4
4
|
Summary: The SQL IDE for Your Terminal.
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
5
|
+
Project-URL: Homepage, https://harlequin.sh
|
|
6
|
+
Project-URL: Documentation, https://harlequin.sh/docs/getting-started/index
|
|
7
|
+
Project-URL: Repository, https://github.com/tconbeer/harlequin
|
|
8
|
+
Project-URL: Bug Tracker, https://github.com/tconbeer/harlequin/issues
|
|
9
|
+
Project-URL: Changelog, https://github.com/tconbeer/harlequin/blob/main/CHANGELOG.md
|
|
10
|
+
Author-email: Ted Conbeer <tconbeer@users.noreply.github.com>
|
|
11
|
+
License-Expression: MIT
|
|
12
|
+
License-File: LICENSE
|
|
13
|
+
Keywords: harlequin,ide,sql,tui
|
|
14
|
+
Requires-Python: <3.14,>=3.9
|
|
15
|
+
Requires-Dist: click==8.1.8
|
|
16
|
+
Requires-Dist: duckdb>=0.8.0
|
|
17
|
+
Requires-Dist: importlib-metadata>=8.0; python_version < '3.10'
|
|
18
|
+
Requires-Dist: numpy<2.1.0,>=2.0.0; python_version < '3.10'
|
|
19
|
+
Requires-Dist: numpy<2.3.0,>=2.1.0; python_version >= '3.10'
|
|
20
|
+
Requires-Dist: platformdirs<5.0,>=3.10
|
|
21
|
+
Requires-Dist: pyarrow>=18.1.0; python_version >= '3.12'
|
|
22
|
+
Requires-Dist: questionary==2.0.1
|
|
23
|
+
Requires-Dist: rich-click==1.8.5
|
|
24
|
+
Requires-Dist: shandy-sqlfmt>=0.19.0
|
|
25
|
+
Requires-Dist: textual-fastdatatable==0.12.0
|
|
26
|
+
Requires-Dist: textual-textarea==0.15.0
|
|
27
|
+
Requires-Dist: textual==0.89.1
|
|
28
|
+
Requires-Dist: tomlkit<0.14.0,>=0.12.5
|
|
29
|
+
Requires-Dist: tree-sitter-sql==0.3.7
|
|
30
|
+
Requires-Dist: tree-sitter<0.25.0,>=0.23.0
|
|
17
31
|
Provides-Extra: adbc
|
|
32
|
+
Requires-Dist: harlequin-adbc; extra == 'adbc'
|
|
18
33
|
Provides-Extra: bigquery
|
|
34
|
+
Requires-Dist: harlequin-bigquery; extra == 'bigquery'
|
|
19
35
|
Provides-Extra: cassandra
|
|
36
|
+
Requires-Dist: harlequin-cassandra; extra == 'cassandra'
|
|
20
37
|
Provides-Extra: databricks
|
|
38
|
+
Requires-Dist: harlequin-databricks; extra == 'databricks'
|
|
21
39
|
Provides-Extra: mysql
|
|
40
|
+
Requires-Dist: harlequin-mysql; extra == 'mysql'
|
|
22
41
|
Provides-Extra: nebulagraph
|
|
42
|
+
Requires-Dist: harlequin-nebulagraph; extra == 'nebulagraph'
|
|
23
43
|
Provides-Extra: odbc
|
|
44
|
+
Requires-Dist: harlequin-odbc; extra == 'odbc'
|
|
24
45
|
Provides-Extra: postgres
|
|
46
|
+
Requires-Dist: harlequin-postgres; extra == 'postgres'
|
|
25
47
|
Provides-Extra: s3
|
|
48
|
+
Requires-Dist: boto3==1.34.22; extra == 's3'
|
|
26
49
|
Provides-Extra: trino
|
|
27
|
-
Requires-Dist:
|
|
28
|
-
Requires-Dist: click (>=8.1.3,<9.0.0)
|
|
29
|
-
Requires-Dist: duckdb (>=0.8.0)
|
|
30
|
-
Requires-Dist: harlequin-adbc (>=0.1) ; extra == "adbc"
|
|
31
|
-
Requires-Dist: harlequin-bigquery (>=1.0.3) ; extra == "bigquery"
|
|
32
|
-
Requires-Dist: harlequin-cassandra (>=0.1.2) ; extra == "cassandra"
|
|
33
|
-
Requires-Dist: harlequin-databricks (>=0.5.2) ; extra == "databricks"
|
|
34
|
-
Requires-Dist: harlequin-mysql (>=1.0) ; extra == "mysql"
|
|
35
|
-
Requires-Dist: harlequin-nebulagraph (>=0.4.1) ; extra == "nebulagraph"
|
|
36
|
-
Requires-Dist: harlequin-odbc (>=0.2) ; extra == "odbc"
|
|
37
|
-
Requires-Dist: harlequin-postgres (>=1.0) ; extra == "postgres"
|
|
38
|
-
Requires-Dist: harlequin-trino (>=0.1) ; extra == "trino"
|
|
39
|
-
Requires-Dist: importlib_metadata (>=8.0) ; python_full_version < "3.10.0"
|
|
40
|
-
Requires-Dist: numpy (>=2.0.0,<2.1.0) ; python_full_version < "3.10.0"
|
|
41
|
-
Requires-Dist: numpy (>=2.1.0,<2.3.0) ; python_full_version >= "3.10.0"
|
|
42
|
-
Requires-Dist: platformdirs (>=3.10,<5.0)
|
|
43
|
-
Requires-Dist: pyarrow (>=18.1.0) ; python_full_version >= "3.12.0"
|
|
44
|
-
Requires-Dist: questionary (>=2.0.1,<3.0.0)
|
|
45
|
-
Requires-Dist: rich-click (>=1.7.1,<2.0.0)
|
|
46
|
-
Requires-Dist: shandy-sqlfmt (>=0.19.0)
|
|
47
|
-
Requires-Dist: textual (==0.89.1)
|
|
48
|
-
Requires-Dist: textual-fastdatatable (==0.12.0)
|
|
49
|
-
Requires-Dist: textual-textarea (==0.15.0)
|
|
50
|
-
Requires-Dist: tomlkit (>=0.12.5,<0.14.0)
|
|
51
|
-
Requires-Dist: tree-sitter (>=0.23.0,<0.25.0)
|
|
52
|
-
Requires-Dist: tree-sitter-sql (==0.3.7)
|
|
53
|
-
Project-URL: Repository, https://github.com/tconbeer/harlequin
|
|
50
|
+
Requires-Dist: harlequin-trino; extra == 'trino'
|
|
54
51
|
Description-Content-Type: text/markdown
|
|
55
52
|
|
|
56
53
|
# Harlequin
|
|
@@ -100,7 +97,7 @@ Alternatively, if you know what you're doing, after installing Python 3.9 or abo
|
|
|
100
97
|
pip install harlequin
|
|
101
98
|
```
|
|
102
99
|
|
|
103
|
-
There is also a [Homebrew formula](https://formulae.brew.sh/formula/harlequin) for Harlequin, although this is maintained by the community and is not as rigorously tested as the Python installations. Note that the formula includes several Harlequin adapter packages (Postgres, MySQL, and ODBC) and their dependencies, which is convenient but increases the application size.
|
|
100
|
+
There is also a [Homebrew formula](https://formulae.brew.sh/formula/harlequin) for Harlequin, although this is maintained by the community and is not as rigorously tested as the Python installations. Note that the formula includes several Harlequin adapter packages (Postgres, MySQL/MariaDB, and ODBC) and their dependencies, which is convenient but increases the application size.
|
|
104
101
|
|
|
105
102
|
```bash
|
|
106
103
|
brew install harlequin
|
|
@@ -110,7 +107,7 @@ brew install harlequin
|
|
|
110
107
|
|
|
111
108
|
Harlequin can connect to dozens of databases using adapter plug-ins. Adapters are distributed as their own Python packages that need to be installed into the same environment as Harlequin.
|
|
112
109
|
|
|
113
|
-
For a list of known adapters provided either by the Harlequin maintainers or the broader community, see the [adapters](adapters) page.
|
|
110
|
+
For a list of known adapters provided either by the Harlequin maintainers or the broader community, see the [adapters](https://harlequin.sh/docs/adapters) page.
|
|
114
111
|
|
|
115
112
|
The adapter docs also include installation instructions. Some adapters can be installed as Harlequin extras, like `postgres`. If you used `uv` to install Harlequin:
|
|
116
113
|
|
|
@@ -154,7 +151,7 @@ To open one or more DuckDB database files, pass in relative or absolute paths as
|
|
|
154
151
|
harlequin "path/to/duck.db" "another_duck.db"
|
|
155
152
|
```
|
|
156
153
|
|
|
157
|
-
If you want to control the version of DuckDB that Harlequin uses, see the [Troubleshooting](troubleshooting/duckdb-version-mismatch) page.
|
|
154
|
+
If you want to control the version of DuckDB that Harlequin uses, see the [Troubleshooting](https://harlequin.sh/docs/troubleshooting/duckdb-version-mismatch) page.
|
|
158
155
|
|
|
159
156
|
## Using Harlequin with SQLite and Other Adapters
|
|
160
157
|
|
|
@@ -170,11 +167,11 @@ You can open one or more SQLite database files by passing in their paths as conn
|
|
|
170
167
|
harlequin -a sqlite "path/to/sqlite.db" "another_sqlite.db"
|
|
171
168
|
```
|
|
172
169
|
|
|
173
|
-
Other adapters can be installed as plug-ins; for more information, see the [installation guide](index#installing-database-adapters), and the guides for individual [adapters](
|
|
170
|
+
Other adapters can be installed as plug-ins; for more information, see the [installation guide](https://harlequin.sh/docs/getting-started/index#installing-database-adapters), and the guides for individual [adapters](https://harlequin.sh/docs/adapters). Each adapter can define its own options, which you can view using `harlequin --help`.
|
|
174
171
|
|
|
175
172
|
## Configuring Harlequin
|
|
176
173
|
|
|
177
|
-
Harlequin contains a large number of options that allow you to [set the theme](
|
|
174
|
+
Harlequin contains a large number of options that allow you to [set the theme](https://harlequin.sh/docs/themes), [customize key bindings](https://harlequin.sh/docs/keymaps/index), [show remote and local files](https://harlequin.sh/docs/files/index), set the locale for number formatting, and much more. These can always be entered at the command line, but it can be convenient to define a configuration as a profile instead. For more information on configuring Harlequin, see [Using Config Files](https://harlequin.sh/docs/config-file/index).
|
|
178
175
|
|
|
179
176
|
## Using Harlequin with Django
|
|
180
177
|
|
|
@@ -198,7 +195,7 @@ harlequin --help
|
|
|
198
195
|
|
|
199
196
|
To view a subset of these docs (and a link back here) from within the app, press <Key>F1</Key>.
|
|
200
197
|
|
|
201
|
-
See the [Troubleshooting](troubleshooting/index) guide for help with key bindings, appearance issues, copy-paste, etc.
|
|
198
|
+
See the [Troubleshooting](https://harlequin.sh/docs/troubleshooting/index) guide for help with key bindings, appearance issues, copy-paste, etc.
|
|
202
199
|
|
|
203
200
|
[GitHub Discussions](https://github.com/tconbeer/harlequin/discussions) are a good place to ask questions, request features, and say hello.
|
|
204
201
|
|
|
@@ -213,4 +210,3 @@ Please consider [sponsoring Harlequin's author](https://github.com/sponsors/tcon
|
|
|
213
210
|
Thanks for your interest in Harlequin! Harlequin is primarily maintained by [Ted Conbeer](https://github.com/tconbeer), but he welcomes all contributions!
|
|
214
211
|
|
|
215
212
|
Please see [`CONTRIBUTING.md`](./CONTRIBUTING.md) for more information.
|
|
216
|
-
|
|
@@ -45,7 +45,7 @@ Alternatively, if you know what you're doing, after installing Python 3.9 or abo
|
|
|
45
45
|
pip install harlequin
|
|
46
46
|
```
|
|
47
47
|
|
|
48
|
-
There is also a [Homebrew formula](https://formulae.brew.sh/formula/harlequin) for Harlequin, although this is maintained by the community and is not as rigorously tested as the Python installations. Note that the formula includes several Harlequin adapter packages (Postgres, MySQL, and ODBC) and their dependencies, which is convenient but increases the application size.
|
|
48
|
+
There is also a [Homebrew formula](https://formulae.brew.sh/formula/harlequin) for Harlequin, although this is maintained by the community and is not as rigorously tested as the Python installations. Note that the formula includes several Harlequin adapter packages (Postgres, MySQL/MariaDB, and ODBC) and their dependencies, which is convenient but increases the application size.
|
|
49
49
|
|
|
50
50
|
```bash
|
|
51
51
|
brew install harlequin
|
|
@@ -55,7 +55,7 @@ brew install harlequin
|
|
|
55
55
|
|
|
56
56
|
Harlequin can connect to dozens of databases using adapter plug-ins. Adapters are distributed as their own Python packages that need to be installed into the same environment as Harlequin.
|
|
57
57
|
|
|
58
|
-
For a list of known adapters provided either by the Harlequin maintainers or the broader community, see the [adapters](adapters) page.
|
|
58
|
+
For a list of known adapters provided either by the Harlequin maintainers or the broader community, see the [adapters](https://harlequin.sh/docs/adapters) page.
|
|
59
59
|
|
|
60
60
|
The adapter docs also include installation instructions. Some adapters can be installed as Harlequin extras, like `postgres`. If you used `uv` to install Harlequin:
|
|
61
61
|
|
|
@@ -99,7 +99,7 @@ To open one or more DuckDB database files, pass in relative or absolute paths as
|
|
|
99
99
|
harlequin "path/to/duck.db" "another_duck.db"
|
|
100
100
|
```
|
|
101
101
|
|
|
102
|
-
If you want to control the version of DuckDB that Harlequin uses, see the [Troubleshooting](troubleshooting/duckdb-version-mismatch) page.
|
|
102
|
+
If you want to control the version of DuckDB that Harlequin uses, see the [Troubleshooting](https://harlequin.sh/docs/troubleshooting/duckdb-version-mismatch) page.
|
|
103
103
|
|
|
104
104
|
## Using Harlequin with SQLite and Other Adapters
|
|
105
105
|
|
|
@@ -115,11 +115,11 @@ You can open one or more SQLite database files by passing in their paths as conn
|
|
|
115
115
|
harlequin -a sqlite "path/to/sqlite.db" "another_sqlite.db"
|
|
116
116
|
```
|
|
117
117
|
|
|
118
|
-
Other adapters can be installed as plug-ins; for more information, see the [installation guide](index#installing-database-adapters), and the guides for individual [adapters](
|
|
118
|
+
Other adapters can be installed as plug-ins; for more information, see the [installation guide](https://harlequin.sh/docs/getting-started/index#installing-database-adapters), and the guides for individual [adapters](https://harlequin.sh/docs/adapters). Each adapter can define its own options, which you can view using `harlequin --help`.
|
|
119
119
|
|
|
120
120
|
## Configuring Harlequin
|
|
121
121
|
|
|
122
|
-
Harlequin contains a large number of options that allow you to [set the theme](
|
|
122
|
+
Harlequin contains a large number of options that allow you to [set the theme](https://harlequin.sh/docs/themes), [customize key bindings](https://harlequin.sh/docs/keymaps/index), [show remote and local files](https://harlequin.sh/docs/files/index), set the locale for number formatting, and much more. These can always be entered at the command line, but it can be convenient to define a configuration as a profile instead. For more information on configuring Harlequin, see [Using Config Files](https://harlequin.sh/docs/config-file/index).
|
|
123
123
|
|
|
124
124
|
## Using Harlequin with Django
|
|
125
125
|
|
|
@@ -143,7 +143,7 @@ harlequin --help
|
|
|
143
143
|
|
|
144
144
|
To view a subset of these docs (and a link back here) from within the app, press <Key>F1</Key>.
|
|
145
145
|
|
|
146
|
-
See the [Troubleshooting](troubleshooting/index) guide for help with key bindings, appearance issues, copy-paste, etc.
|
|
146
|
+
See the [Troubleshooting](https://harlequin.sh/docs/troubleshooting/index) guide for help with key bindings, appearance issues, copy-paste, etc.
|
|
147
147
|
|
|
148
148
|
[GitHub Discussions](https://github.com/tconbeer/harlequin/discussions) are a good place to ask questions, request features, and say hello.
|
|
149
149
|
|
|
@@ -68,6 +68,11 @@ HARLEQUIN_ACTIONS = {
|
|
|
68
68
|
target=None,
|
|
69
69
|
action="toggle_full_screen",
|
|
70
70
|
),
|
|
71
|
+
"show_debug_info": Action(
|
|
72
|
+
target=None,
|
|
73
|
+
action="show_debug_info",
|
|
74
|
+
description="Debug Info",
|
|
75
|
+
),
|
|
71
76
|
"show_query_history": Action(
|
|
72
77
|
target=None,
|
|
73
78
|
action="show_query_history",
|
|
@@ -207,12 +207,21 @@ class HarlequinAdapter(ABC):
|
|
|
207
207
|
disregard any extra (unexpected) kwargs. They should not rely on the
|
|
208
208
|
option's default values, as those will not be passed by the CLI when
|
|
209
209
|
initializing the adapter.
|
|
210
|
+
|
|
211
|
+
Adapters can provide client-side (Harlequin adapter) details using the
|
|
212
|
+
ADAPTER_DETAILS class variable. It is expected to be formatted as markdown.
|
|
213
|
+
|
|
214
|
+
Adapters can also provide server-side (DB driver) details using the
|
|
215
|
+
ADAPTER_DRIVER_DETAILS class variable. It is expected to be formatted
|
|
216
|
+
as markdown.
|
|
210
217
|
"""
|
|
211
218
|
|
|
212
219
|
ADAPTER_OPTIONS: list[HarlequinAdapterOption] | None = None
|
|
213
220
|
COPY_FORMATS: list[HarlequinCopyFormat] | None = None
|
|
214
221
|
"""DEPRECATED. Adapter Copy formats are now ignored by Harlequin."""
|
|
215
222
|
IMPLEMENTS_CANCEL = False
|
|
223
|
+
ADAPTER_DETAILS: str | None = None
|
|
224
|
+
ADAPTER_DRIVER_DETAILS: str | None = None
|
|
216
225
|
|
|
217
226
|
@abstractmethod
|
|
218
227
|
def __init__(self, conn_str: Sequence[str], **options: Any) -> None:
|
|
@@ -267,3 +276,20 @@ class HarlequinAdapter(ABC):
|
|
|
267
276
|
also provide options for customizing the Export dialog GUI.
|
|
268
277
|
"""
|
|
269
278
|
return self.COPY_FORMATS is not None
|
|
279
|
+
|
|
280
|
+
@property
|
|
281
|
+
def provides_details(self) -> bool:
|
|
282
|
+
"""
|
|
283
|
+
True if the adapter provides an optional description of itself, visible
|
|
284
|
+
on Harlequin's debugging info screen, NOT including
|
|
285
|
+
driver or connection details, which should be ADAPTER_DRIVER_DETAILS.
|
|
286
|
+
"""
|
|
287
|
+
return self.ADAPTER_DETAILS is not None
|
|
288
|
+
|
|
289
|
+
@property
|
|
290
|
+
def provides_driver_details(self) -> bool:
|
|
291
|
+
"""
|
|
292
|
+
True if the adapter provides an optional description of its driver
|
|
293
|
+
or connection.
|
|
294
|
+
"""
|
|
295
|
+
return self.ADAPTER_DRIVER_DETAILS is not None
|
|
@@ -57,6 +57,7 @@ from harlequin.catalog_cache import (
|
|
|
57
57
|
from harlequin.components import (
|
|
58
58
|
CodeEditor,
|
|
59
59
|
DataCatalog,
|
|
60
|
+
DebugInfoScreen,
|
|
60
61
|
EditorCollection,
|
|
61
62
|
ErrorModal,
|
|
62
63
|
ExportScreen,
|
|
@@ -69,6 +70,12 @@ from harlequin.components import (
|
|
|
69
70
|
from harlequin.components.confirm_modal import ConfirmModal
|
|
70
71
|
from harlequin.components.data_catalog import ContextMenu
|
|
71
72
|
from harlequin.components.data_catalog.tree import HarlequinTree
|
|
73
|
+
from harlequin.components.debug_info import AdapterDebugInfo, HarlequinDebugInfo
|
|
74
|
+
from harlequin.config import (
|
|
75
|
+
get_config_for_profile,
|
|
76
|
+
get_highest_priority_existing_config_file,
|
|
77
|
+
load_config,
|
|
78
|
+
)
|
|
72
79
|
from harlequin.copy_formats import HARLEQUIN_COPY_FORMATS, WINDOWS_COPY_FORMATS
|
|
73
80
|
from harlequin.driver import HarlequinDriver
|
|
74
81
|
from harlequin.editor_cache import BufferState, Cache
|
|
@@ -182,6 +189,7 @@ class Harlequin(AppBase):
|
|
|
182
189
|
def __init__(
|
|
183
190
|
self,
|
|
184
191
|
adapter: HarlequinAdapter,
|
|
192
|
+
profile_name: str | None = None,
|
|
185
193
|
*,
|
|
186
194
|
keymap_names: Sequence[str] | None = None,
|
|
187
195
|
user_defined_keymaps: Sequence[HarlequinKeyMap] | None = None,
|
|
@@ -201,6 +209,7 @@ class Harlequin(AppBase):
|
|
|
201
209
|
watch_css=watch_css,
|
|
202
210
|
)
|
|
203
211
|
self.adapter = adapter
|
|
212
|
+
self.profile_name = profile_name
|
|
204
213
|
self.connection_hash = connection_hash
|
|
205
214
|
self.history: History | None = None
|
|
206
215
|
self.show_files = show_files
|
|
@@ -279,6 +288,8 @@ class Harlequin(AppBase):
|
|
|
279
288
|
and self.editor._has_focus_within
|
|
280
289
|
):
|
|
281
290
|
self.editor.text_input._pause_blink(visible=True)
|
|
291
|
+
|
|
292
|
+
## TODO: PREVENT DUPLICATE SCREENS HERE.
|
|
282
293
|
return super().push_screen( # type: ignore[no-any-return,call-overload]
|
|
283
294
|
screen,
|
|
284
295
|
callback=callback,
|
|
@@ -951,6 +962,47 @@ class Harlequin(AppBase):
|
|
|
951
962
|
def action_show_help_screen(self) -> None:
|
|
952
963
|
self.push_screen(HelpScreen(id="help_screen"))
|
|
953
964
|
|
|
965
|
+
def action_show_debug_info(self) -> None:
|
|
966
|
+
SCREEN_ID = "debug_info_screen"
|
|
967
|
+
if self.screen.id == SCREEN_ID:
|
|
968
|
+
# already showing this screen.
|
|
969
|
+
return
|
|
970
|
+
|
|
971
|
+
config_path = get_highest_priority_existing_config_file()
|
|
972
|
+
config = load_config(config_path)
|
|
973
|
+
profile_name = self.profile_name
|
|
974
|
+
active_profile_config, _ = get_config_for_profile(config_path, profile_name)
|
|
975
|
+
active_profile_name = profile_name or config.get("default_profile")
|
|
976
|
+
adapter_options = getattr(self.adapter, "ADAPTER_OPTIONS", None)
|
|
977
|
+
adapter_type = type(self.adapter).__name__
|
|
978
|
+
|
|
979
|
+
harlequin_info = HarlequinDebugInfo(
|
|
980
|
+
active_profile_config=active_profile_config,
|
|
981
|
+
active_profile_name=active_profile_name,
|
|
982
|
+
all_keymaps=list(self.all_keymaps.keys()),
|
|
983
|
+
config=config,
|
|
984
|
+
config_path=config_path,
|
|
985
|
+
keymap_names=self.keymap_names,
|
|
986
|
+
theme=self.theme,
|
|
987
|
+
)
|
|
988
|
+
adapter_info = AdapterDebugInfo(
|
|
989
|
+
adapter_options=adapter_options,
|
|
990
|
+
adapter_type=adapter_type,
|
|
991
|
+
adapter_details=self.adapter.ADAPTER_DETAILS
|
|
992
|
+
if self.adapter.provides_details
|
|
993
|
+
else "No details were provided by adapter.",
|
|
994
|
+
adapter_driver_details=self.adapter.ADAPTER_DRIVER_DETAILS
|
|
995
|
+
if self.adapter.provides_driver_details
|
|
996
|
+
else "No details were provided by the database driver.",
|
|
997
|
+
)
|
|
998
|
+
self.push_screen(
|
|
999
|
+
DebugInfoScreen(
|
|
1000
|
+
harlequin_details=harlequin_info.parse_info(),
|
|
1001
|
+
adapter_details=adapter_info.parse_info(),
|
|
1002
|
+
id=SCREEN_ID,
|
|
1003
|
+
)
|
|
1004
|
+
)
|
|
1005
|
+
|
|
954
1006
|
def action_toggle_full_screen(self) -> None:
|
|
955
1007
|
self.full_screen = not self.full_screen
|
|
956
1008
|
|
|
@@ -418,7 +418,9 @@ HelpScreen {
|
|
|
418
418
|
padding: 0;
|
|
419
419
|
}
|
|
420
420
|
|
|
421
|
-
|
|
421
|
+
/* Shared Components */
|
|
422
|
+
|
|
423
|
+
#modal_outer {
|
|
422
424
|
border: round $border-color-focus;
|
|
423
425
|
background: $background;
|
|
424
426
|
margin: 2 4;
|
|
@@ -426,22 +428,22 @@ HelpScreen {
|
|
|
426
428
|
max-width: 88;
|
|
427
429
|
}
|
|
428
430
|
|
|
429
|
-
#
|
|
431
|
+
#modal_header {
|
|
430
432
|
dock: top;
|
|
431
433
|
margin: 0 0 1 0;
|
|
432
434
|
padding: 0 1;
|
|
433
435
|
}
|
|
434
436
|
|
|
435
|
-
#
|
|
437
|
+
#modal_inner {
|
|
436
438
|
border: round $border-color-nofocus;
|
|
437
439
|
padding: 0 0 0 0;
|
|
438
440
|
}
|
|
439
441
|
|
|
440
|
-
#
|
|
442
|
+
#modal_info {
|
|
441
443
|
padding: 0 0 0 0;
|
|
442
444
|
}
|
|
443
445
|
|
|
444
|
-
#
|
|
446
|
+
#modal_footer {
|
|
445
447
|
dock: bottom;
|
|
446
448
|
color: $text-muted;
|
|
447
449
|
margin: 1 0 0 0;
|
|
@@ -618,6 +620,12 @@ HistoryScreen .history-screen--error-label {
|
|
|
618
620
|
text-style: bold italic;
|
|
619
621
|
}
|
|
620
622
|
|
|
623
|
+
/* DEBUG INFO SCREEN */
|
|
624
|
+
|
|
625
|
+
DebugInfoScreen {
|
|
626
|
+
align: center middle;
|
|
627
|
+
padding: 0;
|
|
628
|
+
}
|
|
621
629
|
|
|
622
630
|
/* ConfirmModal */
|
|
623
631
|
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
from harlequin.components.code_editor import CodeEditor, EditorCollection
|
|
2
2
|
from harlequin.components.data_catalog import DataCatalog, HarlequinTree
|
|
3
|
+
from harlequin.components.debug_info import DebugInfoScreen
|
|
3
4
|
from harlequin.components.error_modal import ErrorModal
|
|
4
5
|
from harlequin.components.export_screen import ExportScreen, export_callback
|
|
5
6
|
from harlequin.components.help_screen import HelpScreen
|
|
@@ -15,6 +16,7 @@ __all__ = [
|
|
|
15
16
|
"export_callback",
|
|
16
17
|
"HelpScreen",
|
|
17
18
|
"ResultsTable",
|
|
19
|
+
"DebugInfoScreen",
|
|
18
20
|
"ResultsViewer",
|
|
19
21
|
"RunQueryBar",
|
|
20
22
|
"DataCatalog",
|