Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement tables.get_with_metadata RPC endpoint #3823

Merged
merged 2 commits into from
Sep 11, 2024
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: 2 additions & 0 deletions docs/docs/api/rpc.md
Original file line number Diff line number Diff line change
Expand Up @@ -126,6 +126,8 @@ To use an RPC function:
- import_
- get_import_preview
- list_joinable
- list_with_metadata
- get_with_metadata
- TableInfo
- AddedTableInfo
- SettableTableInfo
Expand Down
28 changes: 25 additions & 3 deletions mathesar/rpc/tables/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
from mathesar.rpc.exceptions.handlers import handle_rpc_exceptions
from mathesar.rpc.tables.metadata import TableMetaDataBlob
from mathesar.rpc.utils import connect
from mathesar.utils.tables import get_tables_meta_data
from mathesar.utils.tables import list_tables_meta_data, get_table_meta_data


class TableInfo(TypedDict):
Expand Down Expand Up @@ -367,15 +367,37 @@ def list_with_metadata(*, schema_oid: int, database_id: int, **kwargs) -> list:
database_id: The Django id of the database containing the table.

Returns:
A list of table details.
A list of table details along with metadata.
"""
user = kwargs.get(REQUEST_KEY).user
with connect(database_id, user) as conn:
tables = get_table_info(schema_oid, conn)

metadata_records = get_tables_meta_data(database_id)
metadata_records = list_tables_meta_data(database_id)
metadata_map = {
r.table_oid: TableMetaDataBlob.from_model(r) for r in metadata_records
}

return [table | {"metadata": metadata_map.get(table["oid"])} for table in tables]


@rpc_method(name="tables.get_with_metadata")
@http_basic_auth_login_required
@handle_rpc_exceptions
def get_with_metadata(*, table_oid: int, database_id: int, **kwargs) -> dict:
"""
Get information about a table in a schema, along with the associated table metadata.

Args:
table_oid: The OID of the table in the user's database.
database_id: The Django id of the database containing the table.

Returns:
A dict describing table details along with its metadata.
"""
user = kwargs.get(REQUEST_KEY).user
with connect(database_id, user) as conn:
table = get_table(table_oid, conn)

raw_metadata = get_table_meta_data(table_oid, database_id)
return TableInfo(table) | {"metadata": TableMetaDataBlob.from_model(raw_metadata)}
4 changes: 2 additions & 2 deletions mathesar/rpc/tables/metadata.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
from modernrpc.auth.basic import http_basic_auth_login_required

from mathesar.rpc.exceptions.handlers import handle_rpc_exceptions
from mathesar.utils.tables import get_tables_meta_data, set_table_meta_data
from mathesar.utils.tables import list_tables_meta_data, set_table_meta_data


class TableMetaDataRecord(TypedDict):
Expand Down Expand Up @@ -90,7 +90,7 @@ def list_(*, database_id: int, **kwargs) -> list[TableMetaDataRecord]:
Returns:
Metadata object for a given table oid.
"""
table_meta_data = get_tables_meta_data(database_id)
table_meta_data = list_tables_meta_data(database_id)
return [
TableMetaDataRecord.from_model(model) for model in table_meta_data
]
Expand Down
4 changes: 2 additions & 2 deletions mathesar/tests/rpc/tables/test_t_metadata.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
def test_tables_meta_data_list(monkeypatch):
database_id = 2

def mock_get_tables_meta_data(_database_id):
def mock_list_tables_meta_data(_database_id):
server_model = Server(id=2, host='example.com', port=5432)
db_model = Database(id=_database_id, name='mymathesardb', server=server_model)
return [
Expand All @@ -27,7 +27,7 @@ def mock_get_tables_meta_data(_database_id):
record_summary_template="{5512} {1223}"
)
]
monkeypatch.setattr(metadata, "get_tables_meta_data", mock_get_tables_meta_data)
monkeypatch.setattr(metadata, "list_tables_meta_data", mock_list_tables_meta_data)

expect_metadata_list = [
metadata.TableMetaDataRecord(
Expand Down
5 changes: 5 additions & 0 deletions mathesar/tests/rpc/test_endpoints.py
Original file line number Diff line number Diff line change
Expand Up @@ -362,6 +362,11 @@
"tables.list_with_metadata",
[user_is_authenticated]
),
(
tables.get_with_metadata,
"tables.get_with_metadata",
[user_is_authenticated]
),
(
tables.patch,
"tables.patch",
Expand Down
20 changes: 17 additions & 3 deletions mathesar/utils/tables.py
Original file line number Diff line number Diff line change
Expand Up @@ -86,16 +86,30 @@ def create_empty_table(name, schema, comment=None):
return table


def get_tables_meta_data(database_id):
def list_tables_meta_data(database_id):
return TableMetaData.objects.filter(database__id=database_id)


def get_table_meta_data(table_oid, database_id):
try:
return TableMetaData.objects.get(
table_oid=table_oid,
database__id=database_id
)
except TableMetaData.DoesNotExist:
return set_table_meta_data(
table_oid=table_oid,
metadata={},
database_id=database_id
)


def set_table_meta_data(table_oid, metadata, database_id):
TableMetaData.objects.update_or_create(
return TableMetaData.objects.update_or_create(
database=Database.objects.get(id=database_id),
data_file=DataFile.objects.get(
id=metadata.pop('data_file_id')
) if metadata.get('data_file_id') is not None else None,
table_oid=table_oid,
defaults=metadata,
)
)[0]
Loading