diff --git a/ibis/backends/__init__.py b/ibis/backends/__init__.py index fb3455c0f45a2..4ec58a23f6de7 100644 --- a/ibis/backends/__init__.py +++ b/ibis/backends/__init__.py @@ -7,7 +7,6 @@ import keyword import re import urllib.parse -import weakref from pathlib import Path from typing import TYPE_CHECKING, Any, ClassVar @@ -47,33 +46,42 @@ class TablesAccessor(collections.abc.Mapping): def __init__(self, backend: BaseBackend) -> None: self._backend = backend - def _execute_if_exists(self, method_name: str) -> list[str]: + def _execute_if_exists( + self, method_name: str, database=None, like=None + ) -> list[str]: """Executes method if it exists and it doesn't raise a NotImplementedError, else returns an empty list.""" method = getattr(self._backend.ddl, method_name) if callable(method): try: - return method() + return method(database=database, like=like) except NotImplementedError: pass return [] - @property - def _tables(self) -> list[str]: + def _gather_tables(self, database=None, like=None) -> list[str]: + """Gathers table names using the list_* methods available on the backend.""" # TODO: break this down into views/tables to be more explicit in repr (see #9859) - # list_* methods that might exist on a given backends + # list_* methods that might exist on a given backends. list_methods = [ "list_tables", "list_temp_tables", "list_views", "list_temp_views", ] - tables = [] for method_name in list_methods: - tables.extend(self._execute_if_exists(method_name)) - + tables.extend( + self._execute_if_exists(method_name, database=database, like=like) + ) return list(set(tables)) + def __call__(self, database=None, like=None): + return self._gather_tables(database, like) + + @property + def _tables(self) -> list[str]: + return self._gather_tables() + def __getitem__(self, name) -> ir.Table: try: return self._backend.table(name) @@ -116,7 +124,7 @@ def _ipython_key_completions_(self) -> list[str]: class DDLAccessor: """ddl accessor list views.""" - def __init__(self, backend: weakref.proxy): + def __init__(self, backend: BaseBackend) -> None: self._backend = backend def _raise_if_not_implemented(self, method_name: str): @@ -1050,10 +1058,10 @@ def tables(self): """ return TablesAccessor(self) - @functools.cached_property + @property def ddl(self): """A ddl accessor.""" - return DDLAccessor(weakref.proxy(self)) + return DDLAccessor(self) @property @abc.abstractmethod diff --git a/ibis/backends/duckdb/__init__.py b/ibis/backends/duckdb/__init__.py index f2540e3ca2f56..f14c414d94ba8 100644 --- a/ibis/backends/duckdb/__init__.py +++ b/ibis/backends/duckdb/__init__.py @@ -1019,8 +1019,17 @@ def _list_temp_tables( ) -> list[str]: """List temporary tables.""" + table_loc = self._warn_and_create_table_loc(database) + + catalog = table_loc.catalog or "temp" + database = table_loc.db or self.current_database + col = "table_name" - where_predicates = [C.table_type.eq("LOCAL TEMPORARY")] + where_predicates = [ + C.table_type.eq("LOCAL TEMPORARY"), + C.table_catalog.eq(sge.convert(catalog)), + C.table_schema.eq(sge.convert(database)), + ] sql = self._list_query_constructor(col, where_predicates) out = self.con.execute(sql).fetch_arrow_table() @@ -1060,7 +1069,7 @@ def _list_temp_views( table_loc = self._warn_and_create_table_loc(database) - catalog = "temp" + catalog = table_loc.catalog or "temp" database = table_loc.db or self.current_database col = "table_name" diff --git a/ibis/backends/duckdb/tests/test_client.py b/ibis/backends/duckdb/tests/test_client.py index 740d4e0fece68..55dc6296cdbc2 100644 --- a/ibis/backends/duckdb/tests/test_client.py +++ b/ibis/backends/duckdb/tests/test_client.py @@ -297,8 +297,6 @@ def test_list_tables_schema_warning_refactor(con): icecream_table = ["ice_cream"] with pytest.warns(FutureWarning): - # I'M HAVING AN ISSUE HERE THAT THE TEST ITSELF RUNS BUT WHEN I RUN - # ALL THE ONES IN THIS FILE I GET EXTRA THINGS COMING IN THE LEFT SIDE assert con.list_tables(schema="shops") == icecream_table assert con.ddl.list_tables(database="shops") == icecream_table