Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ jobs:
- name: Install from TestPyPI
run: pip install --index-url https://test.pypi.org/simple/ --extra-index-url https://pypi.org/simple/ JayDeBeApiArrow
- name: Run mock tests
run: CLASSPATH="test/jars/*" python test/testsuite.py test_mock
run: CLASSPATH="test/jars/*:test/mock-jars/*" python -m pytest test/test_mock.py test/test_infrastructure.py -v

publish-to-pypi:
name: Publish to PyPI
Expand Down
6 changes: 4 additions & 2 deletions CLAUDE.md
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
## Ways of Working
Use `uv run` to run Python scripts and tests — it automatically manages the virtual environment.
- `uv sync` to install/sync dependencies
- `CLASSPATH="test/jars/*" uv run python -m unittest test.test_integration.HsqldbTest` to run integration tests
- `CLASSPATH="test/jars/*:test/mock-jars/*" uv run python -m unittest test.test_mock` to run mock tests
- `uv run bash test/build.sh` to build JARs
- `uv run pytest test/ -v` to run all tests via pytest
- `uv run pytest test/test_postgres.py -v` to run a specific driver's tests
- `uv run pytest test/ -k "test_execute_and_fetch" -v` to run specific tests by name
- `CLASSPATH` is set automatically by tox; for local runs set it to `test/jars/*:test/mock-jars/*`


## Speical Requirements in YOLO Mode
Expand Down
34 changes: 21 additions & 13 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -120,44 +120,52 @@ In theory *every database with a suitable JDBC driver should work*. It is confir

## Testing

Integration tests are located in `test/`. The test suite covers SQLite (in-memory), PostgreSQL, MySQL, and HSQLDB.
Integration tests are located in `test/`. Tests run via [pytest](https://docs.pytest.org/) and cover all supported databases: SQLite (in-memory), HSQLDB, PostgreSQL, MySQL, MSSQL, Oracle, DB2, Trino, and Apache Drill.

### Build JARs and download drivers

```bash
uv run bash test/build.sh # Build arrow-jdbc-extension and MockDriver JARs
uv run bash test/download_jdbc_drivers.sh # Download PostgreSQL, MySQL, SQLite, HSQLDB JDBC drivers
uv run bash test/download_jdbc_drivers.sh # Download JDBC drivers
```

### Run tests

```bash
CLASSPATH="test/jars/*" uv run python -m unittest test.test_integration.HsqldbTest # HSQLDB
CLASSPATH="test/jars/*" uv run python -m unittest test.test_integration.SqliteXerialTest # SQLite
CLASSPATH="test/jars/*" uv run python -m unittest test.test_mock # Mock driver
CLASSPATH="test/jars/*:test/mock-jars/*" uv run pytest test/test_mock.py test/test_infrastructure.py -v # Mock + infrastructure
CLASSPATH="test/jars/*" uv run pytest test/test_hsqldb.py -v # HSQLDB
CLASSPATH="test/jars/*" uv run pytest test/test_sqlite.py::SqliteXerialTest -v # SQLite JDBC
CLASSPATH="test/jars/*" uv run pytest test/ -v --tb=short # All tests
```

Pytest is configured in `pyproject.toml` to run tests in parallel across files using `pytest-xdist` with `--dist loadfile`.

### External database tests

PostgreSQL and MySQL tests require running database instances. Docker Compose configs and helper scripts are provided in `test/`:
Container-based databases are managed via Docker Compose:

```bash
# Start both databases
bash test/start.sh
# Start all databases
cd test && docker compose up -d

# Check status
bash test/status.sh
cd test && docker compose ps

# Stop databases
bash test/stop.sh
# Stop all databases
cd test && docker compose down
```

Database connection defaults (overridable via environment variables):

| Database | Host | Port | DB | User | Password | Env prefix |
|---|---|---|---|---|---|---|
| PostgreSQL | localhost | 5432 | test_db | user | password | `JY_PG_*` |
| MySQL | localhost | 3306 | test_db | user | password | `JY_MYSQL_*` |
| PostgreSQL | localhost | 15432 | test_db | user | password | `JY_PG_*` |
| MySQL | localhost | 13306 | test_db | user | password | `JY_MYSQL_*` |
| MSSQL | localhost | 11433 | — | sa | Password123! | `JY_MSSQL_*` |
| Oracle | localhost | 11521 | XEPDB1 | system | Password123! | `JY_ORACLE_*` |
| DB2 | localhost | 15000 | test_db | db2inst1 | Password123! | `JY_DB2_*` |
| Trino | localhost | 18080 | — | test | — | `JY_TRINO_*` |
| Drill | localhost | 31010 | — | — | — | `JY_DRILL_*` |

## Benchmarks

Expand Down
7 changes: 7 additions & 0 deletions conftest.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import pytest


def pytest_collection_modifyitems(items):
for item in items:
if "test_drill" in item.module.__name__:
item.add_marker(pytest.mark.xdist_group(name="drill"))
7 changes: 7 additions & 0 deletions jaydebeapiarrow/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,10 @@ def _jdbc_connect_jpype(jclassname, url, driver_args, jars, libs, experimental=N

# Add-opens for Apache Arrow on Java 9+
args.append('--add-opens=java.base/java.nio=ALL-UNNAMED')
# Drill's javassist needs reflective access to ClassLoader.defineClass
args.append('--add-opens=java.base/java.lang=ALL-UNNAMED')
# User-supplied extra JVM arguments (e.g. logging suppression)
args.extend(_experimental.get('jvm_args', []))

# jvm_path = ('/usr/lib/jvm/java-6-openjdk'
# '/jre/lib/i386/client/libjvm.so')
Expand Down Expand Up @@ -490,6 +494,9 @@ def connect(jclassname, url, driver_args=None, jars=None, libs=None, experimenta
from JARs after the JVM has already been started, using a
DriverShim proxy. This also bypasses the fork-after-JVM-start
guard, making it suitable for gunicorn --preload workers.
jvm_args (list[str]): Extra JVM arguments passed to startJVM().
Only takes effect on the first connect() call (when the JVM
is started). Ignored on subsequent calls.
"""
if isinstance(driver_args, str):
driver_args = [ driver_args ]
Expand Down
7 changes: 7 additions & 0 deletions jaydebeapiarrow/logging.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
# Java util logging configuration for jaydebeapiarrow.
# Silences noisy third-party JDBC drivers (Drill, Trino, Arrow) that log
# to stdout/stderr during class loading.
handlers=java.util.logging.ConsoleHandler
.level=OFF
java.util.logging.ConsoleHandler.level=OFF
java.util.logging.ConsoleHandler.formatter=java.util.logging.SimpleFormatter
5 changes: 5 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,8 @@ Homepage = "https://github.com/HenryNebula/jaydebeapiarrow"
dev = [
"coverage>=4.5",
"jaydebeapi>=1.2.3",
"pytest>=8.4.2",
"pytest-xdist>=3.8.0",
"unittest-xml-reporting",
]

Expand All @@ -68,3 +70,6 @@ values = ["dev", "rc", "final"]
[tool.setuptools]
packages = ["jaydebeapiarrow", "jaydebeapiarrow.lib"]
include-package-data = true

[tool.pytest.ini_options]
addopts = "-n auto --dist loadfile"
Empty file added test/__init__.py
Empty file.
Loading
Loading