Skip to content

Commit

Permalink
Fix gap in test coverage
Browse files Browse the repository at this point in the history
  • Loading branch information
mesozoic committed Apr 20, 2024
1 parent 54c22c0 commit 513e9b3
Show file tree
Hide file tree
Showing 3 changed files with 58 additions and 7 deletions.
16 changes: 10 additions & 6 deletions pyairtable/orm/model.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
Optional,
Type,
Union,
cast,
)

from typing_extensions import Self as SelfType
Expand Down Expand Up @@ -446,13 +447,16 @@ class _Meta:

@property
def _config(self) -> Mapping[str, Any]:
if not (model_meta := getattr(self.model, "Meta", None)):
if not (meta := getattr(self.model, "Meta", None)):
raise AttributeError(f"{self.model.__name__}.Meta must be defined")
if isinstance(model_meta, dict):
return model_meta
if isinstance(model_meta, type):
return model_meta.__dict__
raise TypeError(type(model_meta))
if isinstance(meta, dict):
return meta
try:
return cast(Mapping[str, Any], meta.__dict__)
except AttributeError:
raise TypeError(
f"{self.model.__name__}.Meta must be a dict or class; got {type(meta)}"
)

def get(
self,
Expand Down
8 changes: 7 additions & 1 deletion pyairtable/testing.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,10 @@
import datetime
import random
import string
from typing import Any, Optional
from typing import Any, Optional, Union

from pyairtable.api import retrying
from pyairtable.api.api import TimeoutTuple
from pyairtable.api.types import AttachmentDict, CollaboratorDict, Fields, RecordDict


Expand Down Expand Up @@ -34,6 +36,8 @@ def fake_meta(
base_id: str = "appFakeTestingApp",
table_name: str = "tblFakeTestingTbl",
api_key: str = "patFakePersonalAccessToken",
timeout: Optional[TimeoutTuple] = None,
retry: Optional[Union[bool, retrying.Retry]] = None,
use_field_ids: bool = False,
) -> type:
"""
Expand All @@ -43,6 +47,8 @@ def fake_meta(
"base_id": base_id,
"table_name": table_name,
"api_key": api_key,
"timeout": timeout,
"retry": retry,
"use_field_ids": use_field_ids,
}
return type("Meta", (), attrs)
Expand Down
41 changes: 41 additions & 0 deletions tests/test_orm_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,47 @@ class Address(Model):
m.assert_not_called()


def test_model_meta_dict():
"""
Test that we can define Meta as a dict rather than a class.
"""

class Address(Model):
Meta = {
"api_key": "fake_api_key",
"base_id": "fake_base_id",
"table_name": "fake_table_name",
"timeout": (1, 1),
"retry": False,
}

assert Address.meta.api.api_key == "fake_api_key"


@pytest.mark.parametrize("invalid_meta", ([1, 2, 3], "invalid", True))
def test_model_invalid_meta(invalid_meta):
"""
Test that model creation raises a TypeError if Meta is an invalid type.
"""
with pytest.raises(TypeError):

class Address(Model):
Meta = invalid_meta


@pytest.mark.parametrize("meta_kwargs", [{"timeout": 1}, {"retry": "sure"}])
def test_model_meta_checks_types(meta_kwargs):
"""
Test that accessing meta raises a TypeError if a value is an invalid type.
"""

class Address(Model):
Meta = fake_meta(**meta_kwargs)

with pytest.raises(TypeError):
Address.meta.api


@pytest.mark.parametrize("name", ("exists", "id"))
def test_model_overlapping(name):
"""
Expand Down

0 comments on commit 513e9b3

Please sign in to comment.