mirror of
https://github.com/simonw/sqlite-utils.git
synced 2026-09-13 20:14:24 +02:00
177 lines
5.5 KiB
Python
177 lines
5.5 KiB
Python
"""
|
|
Tests for SQLite URI filename support
|
|
https://github.com/simonw/sqlite-utils/issues/650
|
|
"""
|
|
import pytest
|
|
import sqlite_utils
|
|
from sqlite_utils import Database
|
|
from click.testing import CliRunner
|
|
from sqlite_utils import cli
|
|
import pathlib
|
|
import tempfile
|
|
import os
|
|
|
|
|
|
@pytest.fixture
|
|
def test_db_file(tmp_path):
|
|
"""Create a test database file with some data"""
|
|
db_path = tmp_path / "test.db"
|
|
db = Database(str(db_path))
|
|
db["test_table"].insert_all([
|
|
{"id": 1, "name": "Alice"},
|
|
{"id": 2, "name": "Bob"},
|
|
{"id": 3, "name": "Charlie"},
|
|
], pk="id")
|
|
db.close()
|
|
return db_path
|
|
|
|
|
|
def test_database_class_with_uri(test_db_file):
|
|
"""Test that Database class can open a URI"""
|
|
# Test read-only mode
|
|
uri = f"file:{test_db_file}?mode=ro"
|
|
db = Database(uri)
|
|
rows = list(db["test_table"].rows)
|
|
assert len(rows) == 3
|
|
assert rows[0]["name"] == "Alice"
|
|
db.close()
|
|
|
|
|
|
def test_database_class_with_uri_immutable(test_db_file):
|
|
"""Test that Database class can open a URI with immutable flag"""
|
|
uri = f"file:{test_db_file}?immutable=1"
|
|
db = Database(uri)
|
|
rows = list(db["test_table"].rows)
|
|
assert len(rows) == 3
|
|
db.close()
|
|
|
|
|
|
def test_database_class_with_uri_multiple_params(test_db_file):
|
|
"""Test URI with multiple query parameters"""
|
|
uri = f"file:{test_db_file}?mode=ro&immutable=1"
|
|
db = Database(uri)
|
|
rows = list(db["test_table"].rows)
|
|
assert len(rows) == 3
|
|
db.close()
|
|
|
|
|
|
def test_cli_tables_with_uri(test_db_file):
|
|
"""Test that tables command works with URI"""
|
|
runner = CliRunner()
|
|
uri = f"file:{test_db_file}?mode=ro"
|
|
result = runner.invoke(cli.cli, ["tables", uri, "--csv"])
|
|
assert result.exit_code == 0
|
|
assert "test_table" in result.output
|
|
|
|
|
|
def test_cli_tables_with_uri_immutable(test_db_file):
|
|
"""Test that tables command works with URI and immutable flag"""
|
|
runner = CliRunner()
|
|
uri = f"file:{test_db_file}?mode=ro&immutable=1"
|
|
result = runner.invoke(cli.cli, ["tables", uri])
|
|
assert result.exit_code == 0
|
|
assert "test_table" in result.output
|
|
|
|
|
|
def test_cli_query_with_uri(test_db_file):
|
|
"""Test that query command works with URI"""
|
|
runner = CliRunner()
|
|
uri = f"file:{test_db_file}?mode=ro"
|
|
result = runner.invoke(cli.cli, ["query", uri, "SELECT * FROM test_table"])
|
|
assert result.exit_code == 0
|
|
assert "Alice" in result.output
|
|
assert "Bob" in result.output
|
|
|
|
|
|
def test_cli_query_with_uri_multiple_params(test_db_file):
|
|
"""Test that query command works with URI with multiple parameters"""
|
|
runner = CliRunner()
|
|
uri = f"file:{test_db_file}?mode=ro&immutable=1"
|
|
result = runner.invoke(cli.cli, ["query", uri, "SELECT name FROM test_table WHERE id = 1"])
|
|
assert result.exit_code == 0
|
|
assert "Alice" in result.output
|
|
|
|
|
|
def test_cli_rows_with_uri(test_db_file):
|
|
"""Test that rows command works with URI"""
|
|
runner = CliRunner()
|
|
uri = f"file:{test_db_file}?mode=ro"
|
|
result = runner.invoke(cli.cli, ["rows", uri, "test_table"])
|
|
assert result.exit_code == 0
|
|
assert "Alice" in result.output
|
|
|
|
|
|
def test_uri_with_relative_path(tmp_path):
|
|
"""Test URI with relative path"""
|
|
# Create a database in a subdirectory
|
|
db_path = tmp_path / "test.db"
|
|
db = Database(str(db_path))
|
|
db["test_table"].insert({"id": 1, "name": "Test"})
|
|
db.close()
|
|
|
|
# Test with relative path in URI
|
|
old_cwd = os.getcwd()
|
|
try:
|
|
os.chdir(tmp_path)
|
|
uri = "file:test.db?mode=ro"
|
|
db = Database(uri)
|
|
rows = list(db["test_table"].rows)
|
|
assert len(rows) == 1
|
|
db.close()
|
|
finally:
|
|
os.chdir(old_cwd)
|
|
|
|
|
|
def test_uri_with_absolute_path(test_db_file):
|
|
"""Test URI with absolute path"""
|
|
# Use triple slash for absolute path
|
|
uri = f"file:///{test_db_file}?mode=ro"
|
|
db = Database(uri)
|
|
rows = list(db["test_table"].rows)
|
|
assert len(rows) == 3
|
|
db.close()
|
|
|
|
|
|
def test_regular_path_still_works(test_db_file):
|
|
"""Ensure regular file paths still work after URI changes"""
|
|
# Test Database class
|
|
db = Database(str(test_db_file))
|
|
rows = list(db["test_table"].rows)
|
|
assert len(rows) == 3
|
|
db.close()
|
|
|
|
# Test CLI
|
|
runner = CliRunner()
|
|
result = runner.invoke(cli.cli, ["tables", str(test_db_file)])
|
|
assert result.exit_code == 0
|
|
assert "test_table" in result.output
|
|
|
|
|
|
def test_cli_insert_with_uri_fails_readonly():
|
|
"""Test that insert fails with read-only URI"""
|
|
runner = CliRunner()
|
|
with runner.isolated_filesystem():
|
|
# Create a database first
|
|
db = Database("test.db")
|
|
db["test_table"].insert({"id": 1, "name": "Test"})
|
|
db.close()
|
|
|
|
# Try to insert with read-only URI
|
|
uri = "file:test.db?mode=ro"
|
|
result = runner.invoke(cli.cli, ["insert", uri, "test_table", "-"],
|
|
input='{"id": 2, "name": "Another"}')
|
|
assert result.exit_code != 0
|
|
assert "readonly" in result.output.lower() or "read-only" in result.output.lower() or "attempt to write" in result.output.lower()
|
|
|
|
|
|
def test_nonexistent_file_with_uri_mode_rwc():
|
|
"""Test that URI with mode=rwc can create new database"""
|
|
runner = CliRunner()
|
|
with runner.isolated_filesystem():
|
|
uri = "file:newdb.db?mode=rwc"
|
|
# This should create the database and table
|
|
result = runner.invoke(cli.cli, ["insert", uri, "test_table", "-"],
|
|
input='{"id": 1, "name": "Test"}')
|
|
assert result.exit_code == 0
|
|
# Verify the database was created
|
|
assert os.path.exists("newdb.db")
|